Our solution is roughly 100 lines of code. We encourage you to work in pairs on this assignment.
In certain games, some strategies are clearly superior to others.
Take for example the case of Hungry Bob and the Free Lunch. Bob knows
that some RSO is providing free lunch today, and it is going to be
either pizza or Chinese food. Bob, being a man of fine taste, prefers
Chinese food. But since Bob is a student, he would much rather have
free pizza than nothing at all. We can model his situation as a
game:
It is clear that Bob is always better off going for the lunch since he always gets a better payoff regardless of whatever the lunch might be. In this case, we say that the 'Don't' strategy is strictly dominated by the 'Go!' strategy.
More formally, we say that Player 1's strategy A is strictly dominated by strategy B when:One can see that if a strategy is strictly dominated, it can never be part of a pure strategy Nash Equilibrium since the player is always better off picking the strategy that dominates it. As a result, by iteratively removing all strictly dominated strategies, we can end up with a game that is easier to analyze.


We are now left with a simpler 1 by 2 game. The same argument holds for Player 2's strategies, which leaves us with only one choice:

Starting here:
'C' is dominated by 'D'
Notice at this point that 'U' does not dominate 'D', nor does 'D' dominate 'U'.
'M' is dominated by 'R'
In our reduced game, 'D' is dominated by 'U', because we only need to
compare the 'U' payoff against the 'D' payoffs for 'L' and the 'U'
payoff against the 'D' payoff for 'R'.
And finally, R is dominated by L
and we're left with one cell!
The examples we provide here give us particularly nice results with
iterative elimination. Some games cannot be simplified to the same
extent. The following game can only be reduced to a 2x2 game:


Your task is to implement the function:
which takes in a Pair[][] (representing a game) and returns a Pair[][] representing the game with strictly dominated strategies iteratively eliminated. To help you get started, we will describe one possible organization of the program. There are other equally valid ways to organize the computation.public static Pair[][] reduceGame(Pair[][] gameData)
Your program will make repeated passes over the game data. Each pass will make (1) a sweep over the rows to identify and then remove rows that are strictly dominated by other rows and (2) a sweep over the columns to identify and then remove columns that are strictly dominated by other columns. Because removing a row (column) can reveal new strictly dominated columns (rows), this process will continue until a full pass is made without reducing the number of rows or columns in the game.
We recommend writing the following four auxiliary functions to simplify your task:
Note: You do not need to use recursion for any of these functions./* Given a game and two rows numbers r1 and r2, * returns true: if payoffs for Player 1 in row r1 are strictly dominated by the * corresponding payoffs for Player 1 in row r2. * returns false: otherwise * * Note: a row never strictly dominates itself. */ public static boolean isRowSD(Pair[][] game, int r1, int r2) /* Given a game and two column numbers c1 and c2, * returns true: if the payoffs for Player 2 in column c1 are strictly dominated by the * corresponding payoffs for Player 2 in column c2. * returns false: otherwise. * * Note: a column never strictly dominates itself. */ public static boolean isColSD(Pair[][] game, boolean int c1, int c2) /* Given a game, completes one sweep over the rows to identify rows are * NOT strictly dominated by other rows and returns a game that includes only * those rows. */ public static Pair[][] rowSweep(Pair[][] game) /* Given a game, complete one sweep over the columns to identify columns that are * NOT strictly dominated by other columns and returns a game that includes * only those columns. */ public static Pair[][] colSweep(Pair[][] game)
We have added two functions to TableUtil to make your lives easier:
To call one of these functions from within ReduceGame.java, prepend its name with TableUtil. as is done in the calls to TableUtil.loadPair and TableUtil.printBoolean in ReduceGame's main function./* copyValidRows: takes a game and a boolean vector that specifies * which rows are valid (row i is valid, if valid[i] is true) and * returns a new matrix that contains only the rows from the game that * are marked as valid * * Note: if all the rows are valid, copyValidRows simply * returns the original game. */ public static Pair[][] copyValidRows(Pair[][] game, boolean[] valid); /* copyValidCols: takes a game and a boolean vector that specifies * which columns are valid and returns a new matrix that contains only * the columns from the game that are marked as valid. * * Note: if all the columns are valid, copyValidCols simply * returns the original game. */ public static Pair[][] copyValidCols(Pair[][] game, boolean[] valid);
We strongly recommend that you write and test your auxiliary functions before putting them together in reduceGame. You can test a function adding code to main to call it with sample arguments and print the expected and actual results. We will give partial credit for auxiliary functions that are implemented correctly and have been tested (simply comment out your test cases). We will not give partial credit for functions that do not work and show no sign of having been tested.
When debugging my solution, I printed out the state of the table after making a sweep over the rows and again after making a sweep of the columns as a way to get a better idea of what was happening in smaller steps.
Check your code into PhoenixForge. We strongly recommend that you check your code into PhoenixForge at regular intervals!