Пример #1
0
int get_shallow_move(int *board, int side) {
    /* Return the move that gives the best position immediately after
     */
    int i;
    int move = 0;
    int score;
    int flips[20];
    int old_board[100];
    int best_score = MIN_SCORE;
    // backup the existing board
    copy_board(board, old_board);
    for (i=11; i<89; ++i) {
        if (legal_move(board,i,side,flips) == 1) {
            make_move(board,i,side,flips);
            score = evaluate_board(board, side, 0);
            if (score > best_score) {
                best_score = score;
                move = i;
            }
            // reset the board before each iteration
            copy_board(old_board, board);
        }
    }
    return move;
}
Пример #2
0
/*
 * This is the main loop of the connect four game.  It first prints a 
 * welcome message, allocates the board, and then begins the game loop
 */
int main()
{
	puts("Welcome to Connect Four\n");

	int* board = new_board();
    
	while (1)
	{
		print_board(board);

		int column = -1;

		// Get human input until they enter a valid choice...
		while (1)
		{
			printf("Enter your move (column number): ");
			scanf("%d", &column);

			if (column < 0 || column >= WIDTH)
			{
				printf("Input a valid choice (0 - 6).\n");
			}
			else if (place(board, column, 1) == 0)
			{
				printf("That column is full.\n");
			}
            else
            {
                break;
            }
		}
        // Did the human input make him or her win?
        if (check_win(board, 1) != 0)
        {
            print_board(board);
            printf("Player 1 wins!\n");
            break;
        }

		// Do the AI's move...
		int ai_column = get_next_move(evaluate_board(board));
		place(board,ai_column, 2);

		// Did the AI's move cause it to win?
        if (check_win(board, 2) != 0)
        {
            print_board(board);
            printf("Player 2 wins!\n");
            break;
        }
	}

	free(board);

	exit(EXIT_SUCCESS);
}
Пример #3
0
int minimize(int *board, int side, int unplayed, int ply) {
    /* Search to depth ply with mutual recursion
     * Side should be the opponent of currently playing side
     * Return the lowest score found
     */
    int old_board[100];
    int flips[20];
    int score = MAX_SCORE;
    if (ply == 0 || test_end(board, unplayed) == 1)
        return evaluate_board(board, side, unplayed);
    copy_board(board, old_board);
    for (int i=11; i<89; ++i) {
        if (legal_move(board, i, side, flips) == 0)
            continue;
        make_move(board, i, side, flips);
        score = MIN(score, maximize(board, -side, 0, ply-1));
        copy_board(old_board, board);
    }
    return score;
}
Пример #4
0
int ab_minimize(int *board, int side, int unplayed, int ply,int a, int b) {
    /* Search to depth ply with mutual recursion
     * Return minimum score possible as opponent of current player
     * Cut off with a and b when possible
     */
    int old_board[100];
    int flips[20];
    if (ply == 0 || test_end(board, unplayed) == 1)
        return evaluate_board(board, side, unplayed);
    copy_board(board, old_board);
    for (int i=11; i<89; ++i) {
        if (legal_move(board, i, side, flips) == 0)
            continue;
        make_move(board, i, side, flips);
        b = MIN(b, ab_maximize(board, -side, 0, ply-1, a, b));
        copy_board(old_board, board);
        if (b <= a)
            break;
    }
    return b;
}
Пример #5
0
int ab_maximize(int *board, int side, int unplayed, int ply, int a,int b) {
    /* Search to depth ply with mutual recursion
     * Return maximum score possible for current side
     * Cuts off search using a and b parameters if possible
     */
    int old_board[100];
    int flips[20];
    if (ply == 0 || test_end(board, unplayed) == 1)
        return evaluate_board(board, side, unplayed);
    copy_board(board, old_board);
    for (int i=11; i<89; ++i) {
        if (legal_move(board, i, side, flips) == 0)
            continue;
        make_move(board, i, side, flips);
        a = MAX(a, ab_minimize(board, -side, 0, ply-1, a, b));
        copy_board(old_board, board);
        if (b <= a)
            // that's a cutoff, no point further pursuing this position
            break;
    }
    return a;
}
Пример #6
0
// Blasphemous! maximize instead of maximise?!
int maximize(int *board, int side, int unplayed, int ply) {
    /* The max portion of minimax
     * Return maximum score available from position
     * Used with currently playing side's turn
     * Search with mutual recursion to depth ply 
     */
    int old_board[100];
    int flips[20];
    int score = MIN_SCORE;
    if (ply == 0 || test_end(board, unplayed) == 1)
        // either reached end of search or game is over, so return
        return evaluate_board(board, side, unplayed);
    // backup the current playing board
    copy_board(board, old_board);
    for (int i=11; i<89; ++i) {
        if (legal_move(board, i, side, flips) == 0)
            continue;
        make_move(board, i, side, flips);
        score = MAX(score, minimize(board, -side, 0, ply-1));
        // reset the board after computing the score
        copy_board(old_board, board);
    }
    return score;
}
Пример #7
0
int main(void)
{
	Color computer_player = -1; // not WHITE or BLACK if we don't play either (e.g. -1)
	int game_on = 0;
	Bitboard *board = malloc(sizeof(Bitboard));
	Undo *u = NULL;
	char* input = malloc(sizeof(char) * max_input_length);
	Move last_move = 0;
	int got_move = 0;

	freopen("/dev/tty", "w", stderr);
	setbuf(stderr, NULL);
	setbuf(stdout, NULL);

	srandom(time(NULL));

	while (1)
	{
		if (game_on && got_move)
		{
			u = malloc(sizeof(Undo));
			board_do_move(board, last_move, u);
			got_move = 0;
		}

		if (game_on && computer_player == board->to_move)
		{
			last_move = search_find_move(board);
			move_srcdest_form(last_move, input);
			printf("move %s\n", input);
			u = malloc(sizeof(Undo));
			board_do_move(board, last_move, u);
		}

		fgets(input, max_input_length, stdin);
		fprintf(stderr, "%s", input);

		if (!strcmp("xboard\n", input))
			printf("feature colors=0 setboard=1 time=0 sigint=0 sigterm=0 variants=\"normal\" done=1\n");
		else if (!strcmp("new\n", input))
		{
			board_free_undos(u);
			board_init(board);
			computer_player = BLACK;
			game_on = 1;
		}
		else if (!strcmp("quit\n", input))
			break;
		else if (!strcmp("force\n", input))
			computer_player = -1;
		else if (!strcmp("go\n", input))
			computer_player = board->to_move;
		else if (!strncmp("setboard ", input, 9))
			board_init_with_fen(board, input + 9);
		else if (!strncmp("result", input, 6))
		{
			computer_player = -1;
			game_on = 0;
		}
		else if (!strncmp("level ", input, 6))
			timer_init(input);
		else if (!strcmp("_print\n", input))
		{
			board_print(board);
			printf("Evaluation: %i\n", evaluate_board(board));
			puts("Pseudolegal moves: ");

			Movelist all_moves;
			move_generate_movelist(board, &all_moves);

			Moveiter it;
			moveiter_init(&it, &all_moves, MOVEITER_SORT_NONE, MOVE_NULL);

			char srcdest_form[6];
			while (moveiter_has_next(&it))
			{
				Move m = moveiter_next(&it);
				move_srcdest_form(m, srcdest_form);
				printf("%s ", srcdest_form);
			}
			puts("\n");
		}
		else if (input[0] >= 'a' && input[0] <= 'h'
				&& input[1] >= '1' && input[1] <= '8'
				&& input[2] >= 'a' && input[2] <= 'h'
				&& input[3] >= '1' && input[3] <= '8')
		{
			last_move = parse_move(board, input);
			if (!last_move)
				printf("Illegal move: %s", input);
			else
				got_move = 1;
		}
		else
			printf("Error (unknown command): %s", input);
	}

	free(board);
	free(input);
	return 0;
}