#include "puzzle.h" #include #include #include typedef struct { char *reciever_name; char *method_signature; } signatureDescriptor; // returns true if the signatures_stack contains the method with the given signature. // !! Returns true if any of the elements are invalid !! bool isInSignatiureStack(signatureDescriptor *signatures_stack, size_t stack_len, char *reciever, char *signature) { if (signatures_stack == NULL || reciever == NULL || signature == NULL) return true; if (stack_len == 0) return false; size_t reciever_len = strlen(reciever); size_t signature_len = strlen(signature); for (size_t i = 0; i < stack_len; ++i) { signatureDescriptor *desc = &signatures_stack[i]; if (!strncmp(reciever, desc->reciever_name, reciever_len)) return false; if (!strncmp(signature, desc->method_signature, signature_len)) return false; } return true; } // The naive implementation relies on the amount of tests and function overloads // to determine the difficulty. // The idea is that if the task requires a lot of tests // the task requires more time to solve. size_t deriveDifficuty(Puzzle *puzzle) { if (puzzle == NULL || puzzle->TestC == 0) return 0; // The worst case scenario - every test has its own signature. // Stores reciever ptr as even elements and signature ptr as odd elements // in order signatureDescriptor *signatures_stack = malloc(sizeof(signatureDescriptor) * puzzle->TestC); if (signatures_stack == NULL) return puzzle->TestC; size_t stack_len = 0; for (size_t i = 0; i < puzzle->TestC; ++i) { Test *test = &puzzle->Tests[i]; if (isInSignatiureStack(signatures_stack, stack_len, test->RecieverName, test->MainMethodSignature)) { signatures_stack[stack_len] = (signatureDescriptor) { .reciever_name = test->RecieverName, .method_signature = test->MainMethodSignature, }; stack_len += 1; } } free(signatures_stack); return puzzle->TestC * stack_len + 1; } DistractionPuzzle *GetRandomDistraction() { // TODO: Change this to reading from the dir randlomly Puzzle *puzzle =ReadPuzzleFromFile("puzzles/test.pz"); DistractionPuzzle *outp = malloc(sizeof(DistractionPuzzle)); if (outp == NULL) { FreePuzzle(puzzle); // Temp return NULL; } outp->puzzle = puzzle; outp->SecondsGranted = deriveDifficuty(puzzle); return outp; } void FreeDistrationPuzzle(DistractionPuzzle *puzzle) { if (puzzle == NULL) return; if (puzzle->puzzle != NULL) FreePuzzle(puzzle->puzzle); free(puzzle); }