static void copiedGamesHasSameAttributes(void) { Game game = exampleStartedGame(); Game *copy = copyGame(&game); assert(game.actualPlayer == copy->actualPlayer); assert(game.status == copy->status); assert(&game != copy); }
/*Determine whether given Move exposes King, if not - Move is valid*/ int isValidMove(Game *game, Move *move){ int res = 0; Color col = getColFromLoc(game->board, move->source); col = oppositeCol(col); Game *copyG = (Game*)malloc(sizeof(Game)); if (copyG== NULL) exitOnError("malloc"); copyGame(game, copyG); updateBoard(copyG, move); if (!canKillKing(copyG, col)){ res = 1; } free(copyG); return res; }
/*Build Minimax Tree of fixed depth via DFS*/ MinimaxNode *getMinimaxTreeFixedDepth(Game *game, int depth, Move *move, Color uCol) { MinimaxNode *curr = (MinimaxNode*)malloc(sizeof(MinimaxNode)); if (curr == NULL) exitOnError("malloc"); curr->game = (Game*)malloc(sizeof(Game)); if (curr->game == NULL) exitOnError("malloc"); struct ListNode *moves; int i = 0; curr->depth = depth; copyGame(game, curr->game); curr->sons = NULL; curr->sonsK = 0; if (move != NULL) { updateBoard(curr->game, move); } if (depth == 1) { curr->move = move; } else { freeMove(move); curr->move = NULL; } if (depth == game->difficulty) { return curr; } if ((depth % 2 == 0 && uCol == WHITE) || (depth % 2 == 1 && uCol == BLACK)) { moves = getMoves(curr->game, WHITE); } else { moves = getMoves(curr->game, BLACK); } int size = listSize(moves); curr->sonsK = size; if (!size) { free(moves); return curr; } else { curr->sons = (MinimaxNode**)malloc(sizeof(MinimaxNode)*size); if (curr->sons == NULL) exitOnError("malloc"); struct ListNode *temp = moves; for (i = 0; i < size; i++) { Move* tMove = copyMove(temp->move); curr->sons[i] = getMinimaxTreeFixedDepth(curr->game, depth + 1, tMove, uCol); temp = temp->next; } freeList(moves); } return curr; }
/*Build Minimax Tree for Best Difficulty using BFS Algorithm*/ MinimaxNode *getMinimaxTreeBestDepth(Game *game, Color uCol) { MinimaxNode *root = (MinimaxNode*)malloc(sizeof(MinimaxNode)); if (root == NULL)exitOnError("malloc"); root->game = (Game*)malloc(sizeof(Game)); if (root->game == NULL) exitOnError("malloc"); root->val = 0; MinimaxNode *curr; ListNode *moves; int i; int leavesLocal = 1; Queue *q = setQueue(); /*Create empty Queue for BFS Traversing*/ int size = 0; root->depth = 0; root->move = NULL; copyGame(game, root->game); root->sons = NULL; root->sonsK = 0; enqueue(q, root); /*While Queue is not empty and there are less than MAX_BOARDS_TO_EVAL Leaves in Tree*/ while (q->size&&leavesLocal + size <= MAX_BOARDS_TO_EVAL) { curr = dequeue(q); /*Pop from Queue*/ if (curr->depth % 2 == 0)moves = getMoves(curr->game, uCol); /*Get possible Moves at current Board state*/ else moves = getMoves(curr->game, oppositeCol(uCol)); size = listSize(moves); if (!size) { free(moves); continue; } curr->sons = (MinimaxNode**)malloc(sizeof(MinimaxNode)*size); if (curr->sons == NULL) exitOnError("malloc"); curr->sonsK = size; ListNode *temp = moves; for (i = 0; i < size; i++) { /*Add Nodes for each possible Move*/ curr->sons[i] = (MinimaxNode*)malloc(sizeof(MinimaxNode)); if (curr->sons[i] == NULL) exitOnError("malloc"); curr->sons[i]->game = (Game*)malloc(sizeof(Game)); if (curr->sons[i]->game == NULL) exitOnError("malloc"); curr->sons[i]->val = 0; copyGame(curr->game, curr->sons[i]->game); Move* tMove = copyMove(temp->move); updateBoard(curr->sons[i]->game, tMove); curr->sons[i]->depth = curr->depth + 1; if (curr->sons[i]->depth == 1) { curr->sons[i]->move = tMove; } else { freeMove(tMove); curr->sons[i]->move = NULL; } curr->sons[i]->sons = NULL; curr->sons[i]->sonsK = 0; enqueue(q, curr->sons[i]); /*Push to Queue*/ temp = temp->next; } /*Update amount of Leaves in Tree*/ freeList(moves); leavesLocal += size; if (size) leavesLocal--; } freeQueue(q); return root; }
int main() { char level_data_line[20*16]; LEVELDATA this_level_data = { {&level_data_line[0], &level_data_line[20], &level_data_line[40], &level_data_line[60], &level_data_line[80], &level_data_line[100],&level_data_line[120],&level_data_line[140], &level_data_line[160],&level_data_line[180],&level_data_line[200],&level_data_line[220], &level_data_line[240],&level_data_line[260],&level_data_line[280],&level_data_line[300]}, 19,11 }; // Initializations srvInit(); // services aptInit(); // applets hidInit(); // input gfxInitDefault(); // gfxSet3D(true); // uncomment if using stereoscopic 3D gfxSetDoubleBuffering(GFX_TOP, true); gfxSetDoubleBuffering(GFX_BOTTOM, false); PrintConsole /*topScreen, */bottomScreen; consoleInit(GFX_BOTTOM, &bottomScreen); // consoleInit(GFX_TOP, &topScreen); clear_char_stack(); int level = 0; int mode = MODE_INIT; // int mode_status = 0; hcount = 0; int timer = 0; // Main loop while (aptMainLoop()) { hidScanInput(); u32 kDown = hidKeysDown(); u32 kUp = hidKeysUp(); u32 kHeld = hidKeysHeld(); if (kDown & KEY_START){ break; // break in order to return to hbmenu } if (mode == MODE_INIT){ // consoleSelect(&topScreen); // printf("\033[2J"); copyGame(level,&this_level_data); gspWaitForVBlank(); printGame(&this_level_data); mode = MODE_GAME; }else if (mode == MODE_CLEAR){ if ((kUp & KEY_A) || (kUp & KEY_B) || (kUp & KEY_X) || (kUp & KEY_Y)){ level++; if (level >= sizeof(level_data)/sizeof(LEVELDATA)) { mode = MODE_ALL_CLEAR; }else{ mode = MODE_INIT; } } if (level < sizeof(level_data)/sizeof(LEVELDATA)) { consoleSelect(&bottomScreen); printf("\033[2J"); printf("\x1b[21;12HStage cleared!!"); printf("\x1b[23;12HPush A to next Next Stage"); } }else if (mode == MODE_ALL_CLEAR){ level = 0; consoleSelect(&bottomScreen); printf("\033[2J"); printf("\x1b[21;12HGame cleared!!!"); printf("\x1b[23;12HPush Start to exit game"); mode = MODE_NULL; }else if (mode == MODE_GAME){ // Your code goes here #ifdef DEBUG consoleSelect(&bottomScreen); if (timer%10==0){ //if (1 != 0){printf("\x1b[10;12HkUp =%08x",(unsigned int)kUp);} //if (1 != 0){printf("\x1b[11;12HkDown=%08x",(unsigned int)kDown);} //if (1 != 0){printf("\x1b[12;12HkHeld=%08x",(unsigned int)kHeld);} //printf("\x1b[22;12HKEY_CPAD_UP=%x",KEY_UP); //printf("\x1b[23;12HKEY_CPAD_DN=%x",KEY_DOWN); printf("\x1b[20;12HRest: [SELECT]"); printf("\x1b[22;12HExit: [START]"); printf("\x1b[24;12HTime: %08d",timer); } timer++; #endif if (kDown != 0 || kHeld != 0){ if (kDown & KEY_SELECT){ mode = MODE_INIT; }else{ moveMan(kDown, kHeld,level,&this_level_data); if(checkCleared(&this_level_data,level)==0){ mode = MODE_CLEAR;} gspWaitForVBlank(); draw_char_stack(this_level_data,spriteData, sizeof(spriteData)/sizeof(SPRITEDATA)); } }else{ gspWaitForVBlank(); } } // Flush and swap framebuffers gfxFlushBuffers(); gfxSwapBuffers(); } gfxExit(); hidExit(); aptExit(); srvExit(); return 0; }
static void copiedGameHasCopiedBoard(void) { Game game = exampleStartedGame(); Game *copy = copyGame(&game); sameBoardsOnDifferentMemoryLocation(©->board, &game.board); }