def game_session(game_id: int, matrix_suite: MatrixSuite, strategies: List[Strategy], proportions: List[List[float]], restarts: int, rounds=1000) -> None: """ Builds the game session according to the given parameters. Parameters: *game_id*: Identifier, it gets printed on console *matrix_suite: The MatrixSuite that the game is played on *strategies*: The set of strategies that will play against each other *proportions*: The probability distribution associated to each strategy for replicator dynamic *restarts*: The number of restart per game session *rounds* The number of rounds per restart, default is 1000 """ print("\n==============================================\n") print("GAME ", game_id, " \n") grand_table = GrandTable(matrix_suite, strategies, restarts, rounds) grand_table.play_games() print(grand_table) # grand_table.to_latex("Game_" + str(game_id)) for i, proportion in enumerate(proportions): replicator_dynamic = ReplicatorDynamic(grand_table) replicator_dynamic.run(proportion, name="Game_" + str(game_id) + "_" + str(i + 1)) print("Gambit test result:") Nash.nash_equilibria(strategies, grand_table)
def continue_sampling(self, matrix): if matrix.profile_dict == {}: return True game = matrix.toGame() decision = False equilibria = [] all_eq = [] for old_eq in self.old_equilibria: new_eq = Nash.replicator_dynamics(game, old_eq, self.iters, self.converge_threshold) decision = decision or linalg.norm(new_eq-old_eq, 2) > self.compare_threshold distances = map(lambda e: linalg.norm(e-new_eq, 2), equilibria) if Regret.regret(game, new_eq) <= self.regret_threshold and \ all([d >= self.dist_threshold for d in distances]): equilibria.append(new_eq) all_eq.append(new_eq) for m in game.biasedMixtures() + [game.uniformMixture()] + \ [game.randomMixture() for __ in range(self.random_restarts)]: eq = Nash.replicator_dynamics(game, m, self.iters, self.converge_threshold) distances = map(lambda e: linalg.norm(e-eq,2), equilibria) if Regret.regret(game, eq) <= self.regret_threshold and \ all([d >= self.dist_threshold for d in distances]): equilibria.append(eq) decision = True all_eq.append(eq) if len(equilibria) == 0: decision = True self.old_equilibria = [min(all_eq, key=lambda e: Regret.regret(game, e))] else: self.old_equilibria = equilibria return decision
def test_mixed_nash(self): expected_eq = np.array([[0.,1.]]) found_eq = N.mixed_nash(self.one_player) self.assertEqual(len(found_eq), 1) self.assertTrue(np.allclose(expected_eq, found_eq[0])) expected_eq = np.array([[1.]]) found_eq = N.mixed_nash(self.one_strategy) self.assertEqual(len(found_eq), 1) self.assertTrue(np.allclose(expected_eq, found_eq[0]))
def single_test(game, noise_model, samples_per_step, delta, alpha, best_effort="false"): old_matrix = ObservationMatrix() for prof in game.knownProfiles(): old_matrix.addObservations(prof, noise_model.generate_samples(game, prof, samples_per_step)) candidate = Nash.mixed_nash(old_matrix.toGame(), at_least_one=True)[0] regret = Regret.regret(game, candidate) data = {"candidate": candidate, "game_eq": regret < delta, "regret": regret, "ne-regrets": {role: {strategy: Regret.regret(game, candidate, role, strategy) for strategy in game.strategies[role]} for role in game.roles}} if best_effort == "true": print 'true' evaluator = BestEffortCIEvaluator(game, [candidate], delta, alpha, BootstrapConfidenceInterval()) else: evaluator = ConfidenceIntervalEvaluator(game, [candidate], delta, alpha, BootstrapConfidenceInterval()) count = samples_per_step target_set = Regret.mixture_neighbors(game, candidate).union(Regret.feasible_profiles(game, candidate)) matrix = ObservationMatrix() for profile in target_set: matrix.addObservations(profile, {r: [PayoffData(s, profile[r][s], data_set) for s, data_set in s_hash.items()] for r, s_hash in old_matrix.profile_dict[profile].items()}) while evaluator.continue_sampling(matrix) and count < 1000: print evaluator.confidence_interval for prof in target_set: matrix.addObservations(prof, noise_model.generate_samples(game, prof, samples_per_step)) count += samples_per_step data["stopping_decision"] = evaluator.get_decision(matrix, candidate) data["sample_count"] = matrix.toGame().max_samples data["final_interval"] = evaluator.confidence_interval print data["final_interval"] return data
def test_SparseRegret(self): clique = S.cliques(self.ss)[0] clique_eq = N.mixed_nash(clique)[0] full_candidate = S.translate(clique_eq, clique, self.ss) self.assertEqual(R.regret(self.ss, full_candidate, deviation="A"), 0) self.assertEqual(R.regret(self.ss, full_candidate, deviation="B"), 0) self.assertEqual(R.regret(self.ss, full_candidate, deviation="C"), 1) self.assertEqual(R.regret(self.ss, full_candidate, deviation="D"), -1) self.assertEqual(R.regret(self.ss, full_candidate), 1)
def test_mixed_nash(self): expected_eq = np.array([[0.,1.]]*2) found_eq = N.mixed_nash(self.pd_str) self.assertEqual(len(found_eq), 1) self.assertTrue(np.allclose(expected_eq, found_eq[0])) expected_eq = np.array([[0.,1.]]) found_eq = N.mixed_nash(self.pd_sym) self.assertEqual(len(found_eq), 1) self.assertTrue(np.allclose(expected_eq, found_eq[0])) expected_eq = np.array([[1./3]*3]*2) found_eq = N.mixed_nash(self.rps_str) self.assertEqual(len(found_eq), 1) self.assertTrue(np.allclose(expected_eq, found_eq[0])) expected_eq = np.array([[1./3]*3]) found_eq = N.mixed_nash(self.rps_sym) self.assertEqual(len(found_eq), 1) self.assertTrue(np.allclose(expected_eq, found_eq[0]))
def continue_sampling(self, matrix): if matrix.profile_dict == {}: return True game = matrix.toGame() decision = True for m in game.biasedMixtures() + [game.uniformMixture()] + \ [game.randomMixture() for __ in range(self.random_restarts)]: eq = Nash.replicator_dynamics(game, m, self.iters, self.converge_threshold) confidence_interval = self.ci_calculator.one_sided_interval(matrix, eq, self.alpha) if confidence_interval < self.delta: self.eq.append(eq) decision = False return decision
def test_pure_nash(self): self.assertEqual(len(N.pure_nash(self.pd_sym)), 1) self.assertEqual(N.pure_nash(self.pd_sym)[0], {"All":{"d":2}}) self.assertEqual(len(N.pure_nash(self.pd_str)), 1) self.assertEqual(N.pure_nash(self.pd_str)[0], {"Alice":{"d":1}, \ "Bob":{"d":1}}) self.assertEqual(len(N.pure_nash(self.rps_sym)), 0) self.assertEqual(len(N.pure_nash(self.rps_str)), 0)
def play_game(): print "calling play_game" games_played = [] global grid, next_grid, games_played for x in range(space_size): for y in range(space_size): current_fox = grid[x][y] if type(current_fox) != Fox: continue for foxB in current_fox.fox_neighbors: if (current_fox.stag_neighbors == 0 and current_fox.rabbit_neighbors) > 0: g.inclusive_cooperate = 0 g.inclusive_defect = 3 g.exclusive_defect = 3 g.exclusive_cooperate = 0 if len(current_fox.fox_neighbors) > 0: if current_fox.stag_neighbors == 0 and current_fox.rabbit_neighbors == 0: continue if (current_fox, foxB ) not in games_played and current_fox is not foxB: g = Nash.Game(current_fox, foxB) if current_fox.stag_neighbors > 0 and current_fox.rabbit_neighbors > 1: g.inclusive_cooperate = 5 g.inclusive_defect = 3 g.exclusive_defect = 0 g.exclusive_cooperate = 3 elif current_fox.stag_neighbors > 0 and current_fox.rabbit_neighbors == 0: g.inclusive_cooperate = 5 g.inclusive_defect = 0 g.exclusive_defect = 0 g.exclusive_cooperate = 0 elif current_fox.stag_neighbors == 0 and current_fox.rabbit_neighbors > 1: g.inclusive_cooperate = 0 g.inclusive_defect = 3 g.exclusive_defect = 0 g.exclusive_cooperate = 3 current_fox.last_score = current_fox.score foxB.last_score = foxB.score g.play() games_played.append((current_fox, foxB)) games_played.append((foxB, current_fox))
def demo(): game = Nash() game.fill_payoff() game.show_payoff() game.find_nash() if game.nash.__len__() == 0: print("game has no nash equilibrium") return else: for n in game.nash: print("({},{})".format(n.x, n.y)) player1 = [] player2 = [] i_0 = random.randint(0, 4) j_0 = random.randint(0, 4) player1.append(game.payoff[i_0][j_0].x) player2.append(game.payoff[i_0][j_0].y) count = 0 while game.is_nash(i_0, j_0) == False and count < 20: i = Player.B_1(j_0, game.payoff) j = Player.B_2(i_0, game.payoff) i_0 = i j_0 = j player1.append(game.payoff[i_0][j_0].x) player2.append(game.payoff[i_0][j_0].y) count += 1 player1.append(game.payoff[i_0][j_0].x) player2.append(game.payoff[i_0][j_0].y) count += 1 x = range(count + 1) player1_curve, = plt.plot(x, player1, label="player 1") player2_curve, = plt.plot(x, player2, label="player 2") plt.legend([player1_curve, player2_curve], ['player 1', 'player 2']) plt.xlabel('attempt of game') plt.ylabel('payoff') plt.grid() plt.show()
action = strat.get_action(1) # Get the next action print("Strategy plays action:" + action.__repr__()) strat.update(1, action, 1.5, 1) # Update the strategy with a fake payoff and opponent action. # Now you might want to look at the class attributes of the strategy, # which you can call the same as functions, just without any parentheses. print("Aselect actions:") print(strat.actions) print() # Test to see if gambit runs properly, see Section 5 of the assignment and Nash.py m = [[3, 0, 5], [1, 0, 1], [3, 1, 3]] print("Gambit test result:") Nash.run_gambit(strategies, m) # The output should be this: # ======================| # Aselect: 1.00 | 1.00 | # Aselect: ---- | ---- | # Aselect: ---- | ---- | # ======================| # Aselect: 1.00 | ---- | # Aselect: ---- | ---- | # Aselect: ---- | 1.00 | # ======================| # Aselect: ---- | 1.00 | # Aselect: ---- | ---- | # Aselect: 1.00 | ---- | # ======================|
def equilibria(self): return Nash.mixed_nash(self.matrix.toGame())
def test_pure_nash(self): self.assertEqual(N.pure_nash(self.one_player)[0], {"All":{"s2":1}}) self.assertEqual(N.pure_nash(self.one_strategy)[0], {"All":{"s1":2}}) self.assertEqual(len(N.pure_nash(self.one_profile)), 0)
print("({},{})".format(n.x,n.y)) i_0 = i j_0 = j count = 0 while game.is_nash(i_0, j_0) == False and count < 20: i = Player.B_1(j_0, game.payoff) j = Player.B_2(i_0, game.payoff) G.add_edge((i_0, j_0), (i, j)) i_0 = i j_0 = j count += 1 game = Nash() # payoff matrix of "oscillating game" # game.payoff = [ # [Tuple(6, 7), Tuple(5, 2), Tuple(5, 8), Tuple(0, 2), Tuple(0, 1)], # [Tuple(1, 1), Tuple(3, 2), Tuple(5, 2), Tuple(1, 3), Tuple(5, 1)], # [Tuple(1, 7), Tuple(2, 7), Tuple(1, 7), Tuple(4, 8), Tuple(8, 1)], # [Tuple(0, 1), Tuple(4, 7), Tuple(8, 2), Tuple(3, 0), Tuple(0, 3)], # [Tuple(8, 4), Tuple(3, 2), Tuple(1, 4), Tuple(9, 6), Tuple(1, 0)] # ] # payoff matrix of "normal game" game.payoff = [ [Tuple(9, 8), Tuple(3, 0), Tuple(4, 2), Tuple(1, 1), Tuple(0, 2)], [Tuple(3, 6), Tuple(9, 3), Tuple(8, 5), Tuple(3, 8), Tuple(9, 6)], [Tuple(8, 9), Tuple(4, 7), Tuple(5, 3), Tuple(4, 4), Tuple(6, 5)], [Tuple(1, 7), Tuple(5, 8), Tuple(9, 4), Tuple(1, 2), Tuple(3, 3)],
i = Player.B_1(j_0, game.payoff) j = Player.B_2(i_0, game.payoff) i_0 = i j_0 = j player1.append(game.payoff[i_0][j_0].x) player2.append(game.payoff[i_0][j_0].y) count += 1 player1.append(game.payoff[i_0][j_0].x) player2.append(game.payoff[i_0][j_0].y) count += 1 x = range(count + 1) return player1, player2, x game = Nash() # payoff matrix of "oscillating game" game.payoff = [ [Tuple(6, 7), Tuple(5, 2), Tuple(5, 8), Tuple(0, 2), Tuple(0, 1)], [Tuple(1, 1), Tuple(3, 2), Tuple(5, 2), Tuple(1, 3), Tuple(5, 1)], [Tuple(1, 7), Tuple(2, 7), Tuple(1, 7),