Beispiel #1
0
// There are two types of command interfaces in the world of computing: good
// interfaces and user interfaces. -- Daniel J. Bernstein
//------------------------------------------------------------------------------
void repl() {
    Position *position = NULL;
    char command[128] = "";

    printf("Donna Vista v%s Copyright (c) 2014-2015 by Michael Dvorkin. All Rights Reserved.\nType ? for help.\n\n", VERSION);
    while (true) {
        printf("donna_vista> ");
        if (fgets(command, sizeof(command), stdin)) {
            // Strip trailing newline returned by fgets().
            int len = strlen(command);
            if (len > 0 && command[len - 1] == '\n') {
                command[len - 1] = '\0';
            }
            if (strlen(command)) {
                if (!strncmp(command, "bench", 5)) {
                    repl_bench(strtok(&command[5], " "));

                } else if (!strncmp(command, "book", 4)) {
                    repl_book(strtok(&command[4], " "));

                } else if (!strncmp(command, "perft", 5)) {
                    repl_perft(strtok(&command[5], " "));

                } else if (!strcmp(command, "go")) {
                    position = repl_think(repl_setup(position));

                } else if (!strcmp(command, "help") || !strcmp(command, "?")) {
                    repl_help();

                } else if (!strcmp(command, "new")) {
                    position = repl_setup(NULL);

                } else if (!strcmp(command, "undo")) {
                    position = repl_undo(position);

                } else if (!strcmp(command, "exit") || !strcmp(command, "quit")) {
                    break;

                } else {
                    Move move = new_move_from_string(position, command);
                    if (move) {
                        position = repl_think(make_move(repl_setup(position), move));
                    } else {
                        char buffer[256];
                        MoveGen *gen = new_move_gen(position);
                        valid_only(generate_all_moves(gen));
                        printf("%s appears to be an invalid move; valid moves are %s\n", command, all_moves(gen, buffer));
                    }
                }
            }
        } else {
            break; // Exit if fgets() errors out.
        }
    }
}
Beispiel #2
0
int main( )
{
    cube< color > c(
        faces< color > { color::blue },
        faces< color > { color::green },
        faces< color > { color::orange },
        faces< color > { color::red },
        faces< color > { color::white },
        faces< color > { color::yellow } );
    std::vector< move > moves =
    {
        { move::up, move::clockwise },
        { move::right, move::flip },
        { move::front, move::clockwise },
        { move::back, move::clockwise },
        { move::right, move::clockwise },
        { move::back, move::flip },
        { move::right, move::clockwise },
        { move::up, move::flip },
        { move::left, move::clockwise },
        { move::back, move::flip },
        { move::right, move::clockwise },
        { move::up, move::counter_clockwise },
        { move::down, move::counter_clockwise },
        { move::right, move::flip },
        { move::front, move::clockwise },
        { move::right, move::counter_clockwise },
        { move::left, move::clockwise },
        { move::back, move::flip },
        { move::up, move::flip },
        { move::front, move::flip }
    };
    c.make_moves( moves.begin( ), moves.end( ) );
    using wild_cube = cube< std::set< color > >;
    auto make_wild_cube = []( ) -> wild_cube
    {
        return
        {
            faces< std::set< color > > { { } },
            faces< std::set< color > > { { } },
            faces< std::set< color > > { { } },
            faces< std::set< color > > { { } },
            faces< std::set< color > > { { } },
            faces< std::set< color > > { { } }
        };
    };
    std::list< wild_cube > middle_steps =
    {
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( ),
        make_wild_cube( )
    };
    auto it = middle_steps.begin( ), end = middle_steps.end( );
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.front[1][1] =
            { c.front[1][1] };
            wc.back[1][1] =
            { c.back[1][1] };
            wc.left[1][1] =
            { c.left[1][1] };
            wc.right[1][1] =
            { c.right[1][1] };
            wc.up[1][1] =
            { c.up[1][1] };
            wc.down[1][1] =
            { c.down[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.down[0][0] =
            wc.down[0][2] =
            wc.down[2][0] =
            wc.down[2][2] =
            { c.down[1][1] };
            wc.front[2][0] =
            wc.front[2][2] =
            { c.front[1][1] };
            wc.left[2][0] =
            wc.left[2][2] =
            { c.left[1][1] };
            wc.right[2][0] =
            wc.right[2][2] =
            { c.right[1][1] };
            wc.back[0][0] =
            wc.back[0][2] =
            { c.back[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.up[0][0] =
            wc.up[0][2] =
            wc.up[2][0] =
            wc.up[2][2] =
            { c.up[1][1] };
            wc.front[0][0] =
            wc.front[0][2] =
            { c.front[1][1] };
            wc.left[0][0] =
            wc.left[0][2] =
            { c.left[1][1] };
            wc.right[0][0] =
            wc.right[0][2] =
            { c.right[1][1] };
            wc.back[2][0] =
            wc.back[2][2] =
            { c.back[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.left[1][2] =
            { c.left[1][1] };
            wc.front[1][0] =
            { c.front[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.left[2][1] =
            { c.left[1][1] };
            wc.down[1][0] =
            { c.down[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.left[1][0] =
            { c.left[1][1] };
            wc.back[1][0] =
            { c.back[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.right[1][0] =
            { c.right[1][1] };
            wc.front[1][2] =
            { c.front[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.right[0][1] =
            { c.right[1][1] };
            wc.up[1][2] =
            { c.up[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.right[2][1] =
            { c.right[1][1] };
            wc.down[1][2] =
            { c.down[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.right[1][2] =
            { c.left[1][1] };
            wc.back[1][2] =
            { c.back[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.front[0][1] =
            wc.front[2][1] =
            {
                c.front[1][1],
                c.back[1][1]
            };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.back[0][1] =
            wc.back[2][1] =
            {
                c.front[1][1],
                c.back[1][1]
            };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.up[0][1] =
            wc.up[2][1] =
            { c.up[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.down[0][1] =
            wc.down[2][1] =
            { c.down[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.front[0][1] =
            wc.front[2][1] =
            { c.front[1][1] };
        } );
    ++it;
    std::for_each(
        it,
        end,
        [&]( wild_cube & wc )
        {
            wc.back[0][1] =
            wc.back[2][1] =
            { c.back[1][1] };
        } );
    assert( it == end );
    auto all_action =
        []( const wild_cube &, auto it ) { std::copy( all_moves( ).begin( ), all_moves( ).end( ), it ); };
    auto f1 =
        []( wild_cube c, move m )
        {
            c.make_move( m );
            return c;
        };
    std::list< wild_cube > finished_middle_steps = middle_steps;
    for ( wild_cube & c : middle_steps ) { c.make_moves( moves.begin( ), moves.end( ) ); }
    while ( ! middle_steps.empty( ) )
    {
        std::list< move > forward, backward;
        AI::biderectional_breadth_first_search< move, move >(
            middle_steps.front( ),
            finished_middle_steps.front( ),
            all_action,
            f1,
            std::back_insert_iterator< decltype( forward ) >( forward ),
            all_action,
            f1,
            std::back_insert_iterator< decltype( backward ) >( backward ) );
        c.make_moves( forward.begin( ), forward.end( ) );
        c.undo_moves( backward.rbegin( ), backward.rend( ) );
        std::cout << c << std::endl;
        middle_steps.pop_front( );
        finished_middle_steps.pop_front( );
        for ( wild_cube & wc : middle_steps )
        {
            wc.make_moves( forward.begin( ), forward.end( ) );
            wc.undo_moves( backward.rbegin( ), backward.rend( ) );
        }
    }
    return 0;
}