def run_tournament(options): botnames = options.players.split(",") bots = [] for botname in botnames: bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * options.repeats playedgames = 0 wins_player1 = 0 wins_player2 = 0 seed = 7453876 print('Playing {} games:'.format(int(totalgames))) for a, b in matches: for r in range(options.repeats): if random.choice([True, False]): p = [a, b] else: p = [b, a] # Generate a state with a random seed state = State.generate(id=seed, phase=int(options.phase)) winner, score = engine.play(bots[p[0]], bots[p[1]], state, options.max_time * 1000, verbose=options.verbose, fast=options.fast) if winner is not None: winner = p[winner - 1] wins[winner] += score if winner == 0: wins_player1 += 1 elif winner == 1: wins_player2 += 1 seed += 1 playedgames += 1 print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format( playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) print('Results:') for i in range(len(bots)): print(' bot {}: {} points'.format(bots[i], wins[i])) print('Player 1 won %d games. Player 2 won %d games.' % (wins_player1, wins_player2))
def run_tournament(options): botnames = options.players.split(",") bots = [] for botname in botnames: bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) ranks = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * options.repeats playedgames = 0 totalpoints = 0 print('Playing {} games:'.format(int(totalgames))) for a, b in matches: for r in range(options.repeats): p = [a, b] if random.choice([True, False]) else [ b, a ] # randomly chooses who starting_state applies to #p = [a, b] # starting state applied to second player #p = [b, a] # starting state applied to first player # add starting_state argument here, most of them apply to second player starting_state = None # None, one_marriage, two marriage, all_jacks, all_aces, same_suit, all_ace_jack state = State.generate(phase=int(options.phase), starting_state=starting_state) winner, score = engine.play(bots[p[0]], bots[p[1]], state, options.max_time * 1000, verbose=False, fast=options.fast) if winner is not None: winner = p[winner - 1] wins[winner] += score ranks[winner] += 1 totalpoints += score playedgames += 1 #print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format(playedgames, totalgames, playedgames/float(totalgames) * 100, wins)) for i in range(len(bots)): ranks[i] = wins[i] / (totalpoints) #ranks[i] = ranks[i]/(totalgames) # i think points are more important than just games won print(' bot {}: {} points, {:04.2f} rank'.format( bots[i], wins[i], ranks[i]))
def call_engine(options): # Create player 1 player1 = util.load_player(options.player1) # Create player 2 player2 = util.load_player(options.player2) # Generate or load the map state, id = State.generate(int(options.num_planets), symmetric=not options.asym) if not options.quiet: print('-- Using map with id {} '.format(id)) print(' Start state: ' + str(state)) # Play the game viz = (options.outputfile.lower() == 'none') outfile = options.outputfile # type: str if not outfile.endswith('.pdf'): outfile += '.pdf' engine.play(player1, player2, state=state, max_time=options.max_time*1000, verbose=(not options.quiet), outfile=outfile)
def call_engine(options): # Create player 1 player1 = util.load_player(options.player1) # Create player 2 player2 = util.load_player(options.player2) # Generate or load the map state = State.generate(phase=int(options.phase)) if not options.quiet: # print('-- Using map with id {} '.format(id)) print(' Start state: ' + str(state)) # Play the game engine.play(player1, player2, state=state, max_time=options.max_time * 1000, verbose=(not options.quiet))
def main(): pool = multiprocessing.pool.ThreadPool(args.parallelism) bots = [] for id, botname in enumerate(args.players): bots.append((id, util.load_player(botname))) wins = [0] * len(bots) games = list(itertools.combinations(bots, 2)) random.shuffle(games) matches = len(games)*args.matches*len(args.planets) rounds = matches * args.rounds log("{} Bots, {} Maps, {} Games, {} Matches, {} Rounds, 1 victor".format(len(bots), len(args.planets), len(games), matches, rounds)) scores = lambda: sorted(zip(wins, args.players), key=lambda x: x[0], reverse=True) try: i = 0 for ret in pool.imap_unordered(execute, gen_rounds(games)): i += 1 (gid, mid, rid), winner, (pid1, pid2), (map_size, seed) = ret if winner is None: result = "DRAW" else: result = args.players[winner] wins[winner] += 1 log("({}:{}:{} | {}:{} | {}:{}): {}".format(gid, mid, rid, map_size, seed, pid1, pid2, result), lvl=2) if i % NOTIFY_AMOUNT == 0: log("Finished {}/{} rounds ({:.2f})%. Current top 3: {}".format(i, rounds, (float(i) / rounds * 100), scores()[:3])) except KeyboardInterrupt: log("Tournament interrupted by user", type="FAIL") pool.terminate() pool.join() sys.exit(1) pool.close() pool.join() log("All games finished", type="SUCCESS") for i, (wins, bot) in enumerate(scores()): log("{:3}. {:20} ({})".format(i, bot, wins))
def main(): pool = multiprocessing.Pool(processes=args.parallelism) bots = [] for id, botname in enumerate(args.players): bots.append(util.load_player(botname)) matches = len(bots) * args.matches * len(args.planets) log("Training against {} Bots, {} Maps, {} Matches".format( len(bots), len(args.planets), matches)) data, target = [], [] try: i = 0 for ret in pool.imap_unordered(execute, gen_rounds(bots)): i += 1 (bid, mid), winner, state_vectors, (map_size, seed) = ret if winner == 1: result = 'won' elif winner == 2: result = 'lost' else: result = 'draw' data += state_vectors target += [result] * len(state_vectors) log("({}:{} | {}:{}): {}".format(bid, mid, map_size, seed, result), lvl=1) if i % NOTIFY_AMOUNT == 0: log("Finished {}/{} matches ({:.2f})%.".format( i, matches, (float(i) / matches * 100))) except KeyboardInterrupt: log("Tournament interrupted by user", type="FAIL") pool.terminate() pool.join() sys.exit(1) pool.close() pool.join() log("All games finished", type="SUCCESS") generate_model(data, target)
def run_tournament(options): botnames = options.players.split(",") bots = [] for botname in botnames: bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) points = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * options.repeats playedgames = 0 print('Playing {} games:'.format(totalgames)) for a, b in matches: for r in range(options.repeats): if random.choice([True, False]): p = [a, b] else: p = [b, a] # Generate a state with a random seed start = State.generate(phase=int(options.phase)) winner = engine.play(bots[p[0]], bots[p[1]], start, verbose=False) #TODO: ALSO IMPLEMENT POINTS FOR WINNING if winner is not None: _, temp_points = winner winner = p[winner[0] - 1] wins[winner] += 1 points[winner] += temp_points playedgames += 1 print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format( playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) print('Results:') for i in range(len(bots)): print(' bot {}: {} wins, {} points'.format(bots[i], wins[i], points[i]))
def run_tournament(options): botnames = options.players.split(",") bots = [] for botname in botnames: bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n*n - n)/2 * options.repeats playedgames = 0 print('Playing {} games:'.format(totalgames)) for a, b in matches: for r in range(options.repeats): if random.choice([True, False]): p = [a, b] else: p = [b, a] start, _ = State.generate(int(options.num_planets), symmetric=not options.asym) winner = engine.play(bots[p[0]], bots[p[1]], start, verbose=False, outfile=None) if winner is not None: winner = p[winner - 1] wins[winner] += 1 playedgames += 1 print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format(playedgames, totalgames, playedgames/float(totalgames) * 100, wins)) print('Results:') for i in range(len(bots)): print(' bot {}: {} wins'.format(bots[i], wins[i]))
def run_tournament(options): rdeep = util.load_player("rdeep") bots = [] for x in range(0, POPULATION): bots.append([util.load_player("evo"), 0]) #print(bots[-1].model.get_weights()[0][8][:10]) for i in range(1, ELITE + 1): exec("boi" + str(i) + " = load_model(\"elite/boi" + str(i) + ".krs\").get_weights()") exec("bots[i - 1][0].set_weights(boi" + str(i) + ")") pass for i in range(0, POPULATION - ELITE): a = eval("np.array(boi" + str(math.ceil((i + 1) / N)) + ")") for a1 in range(len(a)): for a2 in range(len(a[a1])): a[a1][a2] += (random.random() - 0.5) / 10**6 bots[i + ELITE][0].set_weights(a) pass for x in range(0, ELITE): print(bots[x][0].model.get_weights()[0][8][:5]) pass print("*******************************") for x in range(ELITE, POPULATION): print(bots[x][0].model.get_weights()[0][8][:5]) pass n = len(bots) wins = [0] * len(bots) totalgames = POPULATION * options.repeats playedgames = 0 print('Playing {} games:'.format(int(totalgames))) for x in range(0, len(bots)): for j in range(0, options.repeats): # Generate a state with a random seed state = State.generate(id=56, phase=int(options.phase)) winner, score = engine.play(bots[x][0], rdeep, state, options.max_time * 1000, verbose=False, fast=options.fast) if winner is not None: if state.revoked(): bots[x][1] -= 100 print(bots[x][0].turns) bots[x][0].turns = 0 if winner == 1: bots[x][1] += score * 100 for i in range(0, len(bots)): wins[i] = bots[i][1] playedgames += 1 print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format( playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) bots = sorted(bots, key=lambda x: x[1]) print("Average: " + str(sum(wins) / len(wins))) print('Results:') j = 1 for i in range(len(bots)): print(' bot {}: {} points'.format(bots[i][0], bots[i][1])) if i >= len(bots) - ELITE: bots[i][0].model.save("elite/boi" + str(j) + ".krs") j += 1
parser.add_argument("-o", "--opponent", dest="player2", help="the bot to run as your opponent (default: rand)", default="bully") parser.add_argument( "-s", "--seed", dest="seed", type=int, help= "The seed for state generation. Same seed will always return the same state, useful for debugging.", default=None) parser.add_argument("-p", "--phase", dest="phase", type=int, choices=[1, 2], help="The phase the game will start in.", default=1) options = parser.parse_args() state = None player2 = util.load_player(options.player2) app.run(debug=True)
def run_tournament(options): SCOPE = 7 REPEATS = 100 botnames = options.players.split(",") bots = [] exp_bot = 0 for i, botname in enumerate(botnames): if botname.startswith('exp'): exp_bot = i bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) wined_counter = [0] * len(bots) nbr_moves = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * options.repeats * SCOPE * SCOPE playedgames = 0 with open(f"./phase-2/{'-'.join(botnames)}.csv", 'w') as csvf, open(f"./phase-2/{'-'.join(botnames)}.log", 'w') as logf: print('Playing {} games:'.format(int(totalgames))) logf.write('Playing {} games:'.format(int(totalgames))) writer = csv.writer(csvf) writer.writerow([ '#Belief state', '#Depth', '#EXP. bot moves', '#Opponent bot moves', '#EXP. bot wins', '#Opponent bot wins', 'EXP. bot points', 'Total points', '#Total games' ]) for belief_state in range(1, SCOPE): for depth in range(1, SCOPE): bots[exp_bot].__init__(belief_state, depth) for a, b in matches: for _ in range(options.repeats): if random.choice([True, False]): p = [a, b] else: p = [b, a] # Generate a state with a random seed state = State.generate(phase=int(options.phase)) winner, score, [p1_moves, p2_moves] = engine.play( bots[p[0]], bots[p[1]], state, options.max_time * 1000, verbose=False, fast=options.fast) if winner is not None: winner = p[winner - 1] wins[winner] += score if winner == exp_bot: wined_counter[0] += 1 else: wined_counter[1] += 1 nbr_moves[0] += p1_moves nbr_moves[1] += p2_moves playedgames += 1 print('Played {} out of {:.0f} games ({:.0f}%): {} \r'. format(playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) logf.write( 'Played {} out of {:.0f} games ({:.0f}%): {} \r'. format(playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) writer.writerow([ belief_state, depth, nbr_moves[0], nbr_moves[1], wined_counter[0], wined_counter[1], wins[exp_bot], sum(wins), options.repeats ]) wins = [0] * len(bots) wined_counter = [0] * len(bots) print('Last Results:') logf.write('Last Results:') for i in range(len(bots)): print(' bot {}: {} points'.format(bots[i], wins[i])) logf.write(' bot {}: {} points'.format(bots[i], wins[i]))
def run_tournament(options): botnames = options.players.split(",") bots = [] for botname in botnames: bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * options.repeats playedgames = 0 totalScores = [[ botnames[0], botnames[1], 'winner', 'points', f'{botnames[0]} phase1 score', f'{botnames[1]} phase1 score', 'seed' ]] # total scores to output to csv print('Playing {} games:'.format(int(totalgames))) for a, b in matches: for r in range(options.repeats): if random.choice([True, False]): p = [a, b] else: p = [b, a] # Generate a state with a random seed seed = random.randint(0, 100000) state = State.generate(id=seed, phase=int(options.phase)) (winner, score), (player1score, player2score), (player1phase1score, player2phase1score) = engine.play( bots[p[0]], bots[p[1]], state, options.max_time * 1000, verbose=options.verbose, fast=options.fast) if winner is not None: winner = p[winner - 1] wins[winner] += score scores = [0, 0, 0, 0, 0, 0, 0, 0, 0] # initial values for total scores scores[p[0]] = player1score scores[p[1]] = player2score scores[2] = botnames[winner] scores[3] = score scores[p[0] + 4] = player1phase1score scores[p[1] + 4] = player2phase1score scores[6] = seed totalScores.append(scores) playedgames += 1 print(f'Player {bots[p[0]]} scored: {player1score}') print(f'Player {bots[p[1]]} scored: {player2score}') print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format( playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) print() print('Results:') for i in range(len(bots)): print(' bot {}: {} points'.format(bots[i], wins[i])) # output values to csv with open('scores.csv', 'w', newline='') as myfile: wr = csv.writer(myfile, quoting=csv.QUOTE_ALL) for totalScore in totalScores: wr.writerow(totalScore)
# from bots.rdeep import rdeep from bots.dqn.dqn import features import keras from keras.models import Sequential from keras.layers import Dense, Activation from keras import optimizers from keras.models import load_model import numpy as np import random import sys number_of_episodes = 100000 opponent = util.load_player('rdeep') possible_moves = [(None, None)] possible_moves += [(x, None) for x in range(20)] possible_moves += [(None, x) for x in range(20)] possible_moves += [(2, 3), (3, 2), (7, 8), (8, 7), (12, 13), (13, 12), (17, 18), (18, 17)] possible_moves_dict = dict() print(possible_moves) for i, move in enumerate(possible_moves): possible_moves_dict[move] = i def move_hot_form(move):
def run_tournament(options): botnames = options.players.split(",") bots = [] for botname in botnames: bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * options.repeats playedgames = 0 score_list_p1 = [] score_list_p2 = [] print('Playing {} games:'.format(int(totalgames))) for a, b in matches: for r in range(options.repeats): if random.choice([True, False]): p = [a, b] else: p = [b, a] # Generate a state with a random seed state = State.generate(phase=int(options.phase)) winner, score = engine.play(bots[p[0]], bots[p[1]], state, options.max_time * 1000, verbose=False, fast=options.fast) if winner is not None: winner = p[winner - 1] wins[winner] += score playedgames += 1 for index, value in enumerate(wins): if index % 2 != 0: score_list_p2.append(value) else: score_list_p1.append(value) print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format( playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) print('Results:') for i in range(len(bots)): print(' bot {}: {} points'.format(bots[i], wins[i])) # print('p1: {}'.format(score_list_p1)) # print('p2: {}'.format(score_list_p2)) scores_p1_no_cumul = [ score_list_p1[i + 1] - score_list_p1[i] for i in range(len(score_list_p1) - 1) ] scores_p2_no_cumul = [ score_list_p2[i + 1] - score_list_p2[i] for i in range(len(score_list_p2) - 1) ] # if true, plot will show cumulative score. cumulative_plot = True if cumulative_plot is False: score_list_p1_p2 = list(zip(scores_p1_no_cumul, scores_p2_no_cumul)) # print(score_list_p1_p2) else: score_list_p1_p2 = list(zip(score_list_p1, score_list_p2)) # print(score_list_p1_p2) scores_data = pd.DataFrame(score_list_p1_p2, columns=['Player 1 score', 'Player 2 score']) # Calculate the T-test for the means of two independent samples of scores. ttest_result = ttest_ind(scores_data['Player 1 score'], scores_data['Player 2 score']) print(ttest_result) print(scores_data) plt.title('Tournament score of both bots') plt.plot(scores_data.index, scores_data['Player 1 score'], marker='.', label=botnames[0]) plt.plot(scores_data.index, scores_data['Player 2 score'], marker='.', label=botnames[1]) plt.xlabel('Game #') plt.ylabel('Score') plt.legend() # plt.savefig('plot') plt.show()
def create_dataset(path, player=util.load_player(options.player), games=int(options.games), phase=2): """Create a dataset that can be used for training the ML bot model. The dataset is created by having the player (bot) play games against itself. The games parameter indicates how many games will be started. Each game will be played and the game situations will be stored. Then, the game ends and it is recorded whether the game situations resulted in a win or loss for player 1. In other words, each game situation is stored with the corresponding class label (won/lost). Keyword arguments path -- the pathname where the dataset is to be stored player -- the player which will play against itself, default the rand Bot games -- the number of games to play, default 2000 phase -- wheter to start the games in phase 1, the default, or phase 2 """ features = create_features() data = [] target = [] # For progress bar bar_length = 30 start = time.time() for g in range(games - 1): # For progress bar if g % 10 == 0: percent = 100.0 * g / games sys.stdout.write('\r') sys.stdout.write("Generating dataset: [{:{}}] {:>3}%".format( '=' * int(percent / (100.0 / bar_length)), bar_length, int(percent))) sys.stdout.flush() # Randomly generate a state object starting in specified phase. state = State.generate(phase=phase) state_vectors = [] while not state.finished(): # Give the state a signature if in phase 1, obscuring information that a player shouldn't see. given_state = state.clone(signature=state.whose_turn() ) if state.get_phase() == 1 else state # Add the features representation of a state to the state_vectors array state_vectors.append(features(given_state)) # Advance to the next state move = player.get_move(given_state) state = state.next(move) winner, score = state.winner() for state_vector in state_vectors: data.append(state_vector) if winner == 1: result = 'won' elif winner == 2: result = 'lost' target.append(result) with open(path, 'wb') as output: pickle.dump((data, target), output, pickle.HIGHEST_PROTOCOL) # For printing newline after progress bar print( "\nDone. Time to generate dataset: {:.2f} seconds".format(time.time() - start)) return data, target
target.append(result) with open(path, 'wb') as output: pickle.dump((data, target), output, pickle.HIGHEST_PROTOCOL) # For printing newline after progress bar print( "\nDone. Time to generate dataset: {:.2f} seconds".format(time.time() - start)) return data, target if options.overwrite or not os.path.isfile(options.dset_path): create_dataset(options.dset_path, player=util.load_player(options.player), games=int(options.games)) if options.train: # Play around with the model parameters below # HINT: Use tournament fast mode (-f flag) to quickly test your different models. # The following tuple specifies the number of hidden layers in the neural # network, as well as the number of layers, implicitly through its length. # You can set any number of hidden layers, even just one. Experiment and see what works. hidden_layer_sizes = (64, 32) # The learning rate determines how fast we move towards the optimal solution. # A low learning rate will converge slowly, but a large one might overshoot.
def going_first(state): leader = state.leader() return 1 == leader if __name__ == "__main__": REPEATS = 100 PHASE = 2 going_first_num = 0 going_second_num = 0 bot1 = "projectbot" bot2 = "rand" bots = [] bots.append(util.load_player(bot1)) # player1 bots.append(util.load_player(bot2)) # player2 print("Bot1: ", bot1) print("Bot2: ", bot2) n = len(bots) wins = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * REPEATS playedgames = 0 print('Playing {} games:'.format(totalgames)) r = 0
def run_tournament(options): botnames = options.players.split(",") player1 = botnames[0] player2 = botnames[1] bots = [] for botname in botnames: bots.append(util.load_player(botname)) n = len(bots) wins = [0] * len(bots) matches = [(p1, p2) for p1 in range(n) for p2 in range(n) if p1 < p2] totalgames = (n * n - n) / 2 * options.repeats playedgames = 0 print('Playing {} games:'.format(int(totalgames))) output = [] for a, b in matches: for r in range(options.repeats): if random.choice([True, False]): p = [a, b] else: p = [b, a] # Generate a state with a random seed state = State.generate(phase=int(options.phase)) bot_1 = bots[p[0]] bot_2 = bots[p[1]] winner, score = engine.play(bot_1, bot_2, state, options.max_time * 1000, verbose=options.verbose, fast=options.fast) if winner is not None: winner = p[winner - 1] wins[winner] += score winner = bots[winner] if winner == bots[0]: winner = player1 else: winner = player2 print(str([r + 1, winner, score, wins[0], wins[1]])) output.append([r + 1, winner, score, wins[0], wins[1]]) playedgames += 1 print('Played {} out of {:.0f} games ({:.0f}%): {} \r'.format( playedgames, totalgames, playedgames / float(totalgames) * 100, wins)) file_name = str(player1) + " vs " + str(player2) + " for " + str( options.repeats) + " games.csv" with open(file_name, mode='w') as out_file: file_writer = csv.writer(out_file, delimiter=',', quotechar='"', quoting=csv.QUOTE_MINIMAL) file_writer.writerow( ['Game no.', 'Winner', 'Score', str(player1), str(player2)]) for row in output: file_writer.writerow(row) print('Results:') for i in range(len(bots)): print(' bot {}: {} points'.format(bots[i], wins[i]))