Merge remote-tracking branch 'origin/Krisp' into tobi_experimental
This commit is contained in:
commit
6aa59ce710
89
bintree.c
89
bintree.c
@ -13,42 +13,50 @@
|
|||||||
// ordering. Accepts duplicates if isDuplicate is NULL, otherwise ignores
|
// ordering. Accepts duplicates if isDuplicate is NULL, otherwise ignores
|
||||||
// duplicates and sets isDuplicate to 1 (or to 0 if a new entry is added).
|
// duplicates and sets isDuplicate to 1 (or to 0 if a new entry is added).
|
||||||
|
|
||||||
void copyData(void *dest, const void *src, size_t size) {
|
TreeNode *createTreeNode(const void *data, size_t dataSize) {
|
||||||
unsigned char *d = dest;
|
TreeNode *node =
|
||||||
const unsigned char *s = src;
|
malloc(sizeof(TreeNode)); // Speicher für neuen Knoten reservieren
|
||||||
for (size_t i = 0; i < size; i++) {
|
if (node == NULL)
|
||||||
d[i] = s[i];
|
return NULL; // Abbrechen bei Fehler
|
||||||
|
|
||||||
|
node->data = malloc(dataSize); // Speicher für Daten reservieren
|
||||||
|
if (node->data == NULL) {
|
||||||
|
free(node);
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
memcpy(node->data, data, dataSize); // Standardfunktion string.h, kopiert
|
||||||
|
// size bytes von data nach node->data,
|
||||||
|
// daten dürfen sich nicht überschneiden
|
||||||
|
// speichern der Daten in node->data
|
||||||
|
node->left = NULL; // Kinder sind NULL
|
||||||
|
node->right = NULL;
|
||||||
|
return node;
|
||||||
}
|
}
|
||||||
|
|
||||||
TreeNode *addToTree(TreeNode *root, const void *data, size_t dataSize,
|
TreeNode *addToTree(TreeNode *root, const void *data, size_t dataSize,
|
||||||
CompareFctType compareFct, int *isDuplicate) {
|
CompareFctType compareFct, int *isDuplicate) {
|
||||||
|
|
||||||
// isDuplicate initialisieren (auf 0 setzen)
|
// isDuplicate initialisieren (auf 0 setzen), verhindert Änderung am Baum
|
||||||
if (isDuplicate) {
|
if (isDuplicate) {
|
||||||
*isDuplicate = 0;
|
*isDuplicate = 0;
|
||||||
}
|
} // bei 0: neuer Wert wurde eingefügt, bei 1: Wert war bereits im Baum
|
||||||
|
|
||||||
// leerer Baum
|
// leerer Baum
|
||||||
if (root == NULL) {
|
if (root == NULL) {
|
||||||
TreeNode *node = malloc(sizeof(TreeNode));
|
return createTreeNode(data, dataSize);
|
||||||
node->data = malloc(dataSize);
|
|
||||||
copyData(node->data, data, dataSize);
|
|
||||||
node->left = NULL;
|
|
||||||
node->right = NULL;
|
|
||||||
return node;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// mit compareFct <0 links >0 rechts =0 Duplikat
|
// mit compareFct <0 links >0 rechts =0 Duplikat
|
||||||
int cmp = compareFct(data, root->data);
|
int compare = compareFct(data, root->data);
|
||||||
|
|
||||||
if (cmp < 0) {
|
if (compare < 0) { // Eintrag links
|
||||||
root->left = addToTree(root->left, data, dataSize, compareFct, isDuplicate);
|
root->left = addToTree(root->left, data, dataSize, compareFct, isDuplicate);
|
||||||
} else if (cmp > 0) {
|
} else if (compare > 0) { // Eintrag rechts
|
||||||
root->right =
|
root->right =
|
||||||
addToTree(root->right, data, dataSize, compareFct, isDuplicate);
|
addToTree(root->right, data, dataSize, compareFct, isDuplicate);
|
||||||
} else {
|
} else { // Duplikat
|
||||||
// isDuplicate auf 1 setzen
|
// isDuplicate auf 1 setzen, keine Änderung am Baum
|
||||||
if (isDuplicate) {
|
if (isDuplicate) {
|
||||||
*isDuplicate = 1;
|
*isDuplicate = 1;
|
||||||
}
|
}
|
||||||
@ -62,52 +70,57 @@ TreeNode *addToTree(TreeNode *root, const void *data, size_t dataSize,
|
|||||||
// the root node and all left nodes first. On returning the next element, push
|
// the root node and all left nodes first. On returning the next element, push
|
||||||
// the top node and push all its left nodes.
|
// the top node and push all its left nodes.
|
||||||
void *nextTreeData(TreeNode *root) {
|
void *nextTreeData(TreeNode *root) {
|
||||||
static StackNode *stack = NULL;
|
static StackNode *stack = NULL; // static -> behält Wert bei mehreren Aufrufen
|
||||||
|
|
||||||
// Neue Iteration starten
|
// Neue Iteration starten
|
||||||
if (root != NULL) {
|
if (root != NULL) {
|
||||||
clearStack(&stack);
|
clearStack(&stack); // alte Stack-Inhalte werden gelöscht
|
||||||
|
|
||||||
TreeNode *curr = root;
|
TreeNode *currentNode = root;
|
||||||
while (curr != NULL) {
|
while (currentNode !=
|
||||||
|
NULL) { // alle linken Knoten werden vom root an auf den Stack gelegt
|
||||||
StackNode *oldStack = stack;
|
StackNode *oldStack = stack;
|
||||||
StackNode *newStack = push(stack, curr);
|
StackNode *newStack = push(stack, currentNode);
|
||||||
if (newStack == oldStack)
|
if (newStack == oldStack)
|
||||||
return NULL; // push fehlgeschlagen
|
return NULL; // push fehlgeschlagen
|
||||||
stack = newStack;
|
stack = newStack;
|
||||||
curr = curr->left;
|
currentNode = currentNode->left;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (stack == NULL)
|
if (stack == NULL)
|
||||||
return NULL; // alles durchlaufen
|
return NULL; // wenn Stack leer ist sind keine Elemente mehr vorhanden,
|
||||||
|
// Iteration beendet
|
||||||
|
|
||||||
// Oberstes Element abrufen
|
// oberster Knoten vom Stack
|
||||||
TreeNode *node = (TreeNode *)top(stack);
|
TreeNode *node = top(stack);
|
||||||
stack = pop(stack);
|
stack = pop(stack);
|
||||||
|
|
||||||
// Rechten Teilbaum pushen
|
// Rechten Teilbaum pushen
|
||||||
TreeNode *curr = node->right;
|
TreeNode *currentNode = node->right;
|
||||||
while (curr != NULL) {
|
while (currentNode != NULL) {
|
||||||
StackNode *oldStack = stack;
|
StackNode *oldStack = stack;
|
||||||
StackNode *newStack = push(stack, curr);
|
StackNode *newStack = push(stack, currentNode);
|
||||||
if (newStack == oldStack)
|
if (newStack == oldStack)
|
||||||
return NULL; // push fehlgeschlagen
|
return NULL; // push fehlgeschlagen
|
||||||
stack = newStack;
|
stack = newStack;
|
||||||
curr = curr->left;
|
currentNode = currentNode->left;
|
||||||
}
|
}
|
||||||
return node->data;
|
return node->data; // Pointer auf Daten
|
||||||
}
|
}
|
||||||
|
|
||||||
// Releases all memory resources (including data copies).
|
// Releases all memory resources (including data copies).
|
||||||
void clearTree(TreeNode *root) {
|
void clearTree(TreeNode **root) { // rekursive Funktion zum freigeben des
|
||||||
if (root == NULL)
|
// Speichers und Nullsetzen der Pointer
|
||||||
|
if (root == NULL || *root == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
clearTree(root->left);
|
clearTree(&(*root)->left); // linken Teilbaum löschen
|
||||||
clearTree(root->right);
|
clearTree(&(*root)->right); // rechten Teilbaum löschen
|
||||||
|
|
||||||
free(root->data);
|
free((*root)->data); // Daten freigeben
|
||||||
free(root);
|
(*root)->data = NULL;
|
||||||
|
free(*root); // Knoten freigeben
|
||||||
|
*root = NULL; // Zeiger auf NULL setzen
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns the number of entries in the tree given by root.
|
// Returns the number of entries in the tree given by root.
|
||||||
|
|||||||
@ -11,7 +11,7 @@ typedef struct node {
|
|||||||
struct node *right;
|
struct node *right;
|
||||||
} TreeNode;
|
} TreeNode;
|
||||||
|
|
||||||
void copyData(void *dest, const void *src, size_t size);
|
TreeNode *createTreeNode(const void *data, size_t dataSize);
|
||||||
|
|
||||||
// Adds a copy of data's pointer destination to the tree using compareFct for
|
// Adds a copy of data's pointer destination to the tree using compareFct for
|
||||||
// ordering. Accepts duplicates if isDuplicate is NULL, otherwise ignores
|
// ordering. Accepts duplicates if isDuplicate is NULL, otherwise ignores
|
||||||
@ -25,7 +25,7 @@ TreeNode *addToTree(TreeNode *root, const void *data, size_t dataSize,
|
|||||||
// the top node and push all its left nodes.
|
// the top node and push all its left nodes.
|
||||||
void *nextTreeData(TreeNode *root);
|
void *nextTreeData(TreeNode *root);
|
||||||
// Releases all memory resources (including data copies).
|
// Releases all memory resources (including data copies).
|
||||||
void clearTree(TreeNode *root);
|
void clearTree(TreeNode **root);
|
||||||
// Returns the number of entries in the tree given by root.
|
// Returns the number of entries in the tree given by root.
|
||||||
unsigned int treeSize(const TreeNode *root);
|
unsigned int treeSize(const TreeNode *root);
|
||||||
|
|
||||||
|
|||||||
85
highscore.c
85
highscore.c
@ -1,23 +1,22 @@
|
|||||||
#include <stdlib.h>
|
|
||||||
#include <stdio.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include "highscore.h"
|
#include "highscore.h"
|
||||||
#include "bintree.h"
|
#include "bintree.h"
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
#define MAX_LINE_LEN 100
|
#define MAX_LINE_LEN 100
|
||||||
#define MAX_PLAYER_NAME_LEN 20
|
#define MAX_PLAYER_NAME_LEN 20
|
||||||
|
|
||||||
typedef struct
|
typedef struct {
|
||||||
{
|
|
||||||
char name[MAX_PLAYER_NAME_LEN];
|
char name[MAX_PLAYER_NAME_LEN];
|
||||||
int score;
|
int score;
|
||||||
} HighscoreEntry;
|
} HighscoreEntry;
|
||||||
|
|
||||||
static TreeNode *highscoreTree = NULL;
|
static TreeNode *highscoreTree = NULL;
|
||||||
|
|
||||||
// Compare two highscore entries by score (descending), then by name (ascending).
|
// Compare two highscore entries by score (descending), then by name
|
||||||
static int compareHighscoreEntries(const void *arg1, const void *arg2)
|
// (ascending).
|
||||||
{
|
static int compareHighscoreEntries(const void *arg1, const void *arg2) {
|
||||||
const HighscoreEntry *entry1 = (const HighscoreEntry *)arg1;
|
const HighscoreEntry *entry1 = (const HighscoreEntry *)arg1;
|
||||||
const HighscoreEntry *entry2 = (const HighscoreEntry *)arg2;
|
const HighscoreEntry *entry2 = (const HighscoreEntry *)arg2;
|
||||||
|
|
||||||
@ -30,12 +29,10 @@ static int compareHighscoreEntries(const void *arg1, const void *arg2)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Create a new highscore entry from name and score.
|
// Create a new highscore entry from name and score.
|
||||||
static HighscoreEntry createHighscoreEntry(const char *name, int score)
|
static HighscoreEntry createHighscoreEntry(const char *name, int score) {
|
||||||
{
|
|
||||||
HighscoreEntry entry = {"", score};
|
HighscoreEntry entry = {"", score};
|
||||||
|
|
||||||
if(name != NULL)
|
if (name != NULL) {
|
||||||
{
|
|
||||||
strncpy(entry.name, name, MAX_PLAYER_NAME_LEN);
|
strncpy(entry.name, name, MAX_PLAYER_NAME_LEN);
|
||||||
entry.name[MAX_PLAYER_NAME_LEN - 1] = '\0';
|
entry.name[MAX_PLAYER_NAME_LEN - 1] = '\0';
|
||||||
}
|
}
|
||||||
@ -44,29 +41,26 @@ static HighscoreEntry createHighscoreEntry(const char *name, int score)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Calculate score based on time used and number of shown numbers.
|
// Calculate score based on time used and number of shown numbers.
|
||||||
static int calculateScore(double timeInSeconds, unsigned int len)
|
static int calculateScore(double timeInSeconds, unsigned int len) {
|
||||||
{
|
|
||||||
return (1000.0 - timeInSeconds) * len;
|
return (1000.0 - timeInSeconds) * len;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Load highscores from file into memory.
|
// Load highscores from file into memory.
|
||||||
void loadHighscores(const char *path)
|
void loadHighscores(const char *path) {
|
||||||
{
|
|
||||||
FILE *file = fopen(path, "r");
|
FILE *file = fopen(path, "r");
|
||||||
|
|
||||||
if(file != NULL)
|
if (file != NULL) {
|
||||||
{
|
|
||||||
char buffer[MAX_LINE_LEN + 1];
|
char buffer[MAX_LINE_LEN + 1];
|
||||||
|
|
||||||
while(fgets(buffer, MAX_LINE_LEN+1, file) != NULL)
|
while (fgets(buffer, MAX_LINE_LEN + 1, file) != NULL) {
|
||||||
{
|
|
||||||
char *name = strtok(buffer, ";\n");
|
char *name = strtok(buffer, ";\n");
|
||||||
char *scoreStr = strtok(NULL, ";\n");
|
char *scoreStr = strtok(NULL, ";\n");
|
||||||
|
|
||||||
if(name != NULL && scoreStr != NULL)
|
if (name != NULL && scoreStr != NULL) {
|
||||||
{
|
HighscoreEntry entry =
|
||||||
HighscoreEntry entry = createHighscoreEntry(name, strtol(scoreStr, NULL, 10));
|
createHighscoreEntry(name, strtol(scoreStr, NULL, 10));
|
||||||
highscoreTree = addToTree(highscoreTree, &entry, sizeof(entry), compareHighscoreEntries, NULL);
|
highscoreTree = addToTree(highscoreTree, &entry, sizeof(entry),
|
||||||
|
compareHighscoreEntries, NULL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -75,19 +69,23 @@ void loadHighscores(const char *path)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Add a new highscore entry and return the calculated score.
|
// Add a new highscore entry and return the calculated score.
|
||||||
int addHighscore(const char *name, double timeInSeconds, unsigned int len)
|
int addHighscore(const char *name, double timeInSeconds, unsigned int len) {
|
||||||
{
|
HighscoreEntry entry =
|
||||||
HighscoreEntry entry = createHighscoreEntry(name, calculateScore(timeInSeconds, len));
|
createHighscoreEntry(name, calculateScore(timeInSeconds, len));
|
||||||
highscoreTree = addToTree(highscoreTree, &entry, sizeof(entry), compareHighscoreEntries, NULL);
|
highscoreTree = addToTree(highscoreTree, &entry, sizeof(entry),
|
||||||
|
compareHighscoreEntries, NULL);
|
||||||
|
|
||||||
return entry.score;
|
return entry.score;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Print highscores (up to NUMBER_OF_SHOWN_HIGHSCORES) in a formatted table.
|
// Print highscores (up to NUMBER_OF_SHOWN_HIGHSCORES) in a formatted table.
|
||||||
void showHighscores()
|
void showHighscores() {
|
||||||
{
|
const char *blanks =
|
||||||
const char *blanks = " ";
|
" "
|
||||||
const char *stripes = "------------------------------------------------------------------------------------------------------------------------";
|
" ";
|
||||||
|
const char *stripes =
|
||||||
|
"------------------------------------------------------------------------"
|
||||||
|
"------------------------------------------------";
|
||||||
const char *header = "H I G H S C O R E S";
|
const char *header = "H I G H S C O R E S";
|
||||||
const int lineWidth = MAX_PLAYER_NAME_LEN + MAX_PLAYER_NAME_LEN + 5;
|
const int lineWidth = MAX_PLAYER_NAME_LEN + MAX_PLAYER_NAME_LEN + 5;
|
||||||
|
|
||||||
@ -96,28 +94,26 @@ void showHighscores()
|
|||||||
HighscoreEntry *entry = nextTreeData(highscoreTree);
|
HighscoreEntry *entry = nextTreeData(highscoreTree);
|
||||||
|
|
||||||
printf("+%*.*s+\n", lineWidth, lineWidth, stripes);
|
printf("+%*.*s+\n", lineWidth, lineWidth, stripes);
|
||||||
printf("|%*.*s%s%*.*s|\n", blankSpace, blankSpace, blanks, header, blankSpace, blankSpace, blanks);
|
printf("|%*.*s%s%*.*s|\n", blankSpace, blankSpace, blanks, header, blankSpace,
|
||||||
|
blankSpace, blanks);
|
||||||
printf("+%*.*s+\n", lineWidth, lineWidth, stripes);
|
printf("+%*.*s+\n", lineWidth, lineWidth, stripes);
|
||||||
|
|
||||||
for(int i = 0; i < NUMBER_OF_SHOWN_HIGHSCORES && entry != NULL; i++)
|
for (int i = 0; i < NUMBER_OF_SHOWN_HIGHSCORES && entry != NULL; i++) {
|
||||||
{
|
printf("| %-*s | %*d |\n", MAX_PLAYER_NAME_LEN, entry->name,
|
||||||
printf("| %-*s | %*d |\n", MAX_PLAYER_NAME_LEN, entry->name, MAX_PLAYER_NAME_LEN, entry->score);
|
MAX_PLAYER_NAME_LEN, entry->score);
|
||||||
printf("+%*.*s+\n", lineWidth, lineWidth, stripes);
|
printf("+%*.*s+\n", lineWidth, lineWidth, stripes);
|
||||||
entry = nextTreeData(NULL);
|
entry = nextTreeData(NULL);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Save highscores to file (up to NUMBER_OF_SHOWN_HIGHSCORES).
|
// Save highscores to file (up to NUMBER_OF_SHOWN_HIGHSCORES).
|
||||||
void saveHighscores(const char *path)
|
void saveHighscores(const char *path) {
|
||||||
{
|
|
||||||
FILE *file = fopen(path, "w");
|
FILE *file = fopen(path, "w");
|
||||||
|
|
||||||
if(file != NULL)
|
if (file != NULL) {
|
||||||
{
|
|
||||||
HighscoreEntry *entry = nextTreeData(highscoreTree);
|
HighscoreEntry *entry = nextTreeData(highscoreTree);
|
||||||
|
|
||||||
for(int i = 0; i < NUMBER_OF_SHOWN_HIGHSCORES && entry != NULL; i++)
|
for (int i = 0; i < NUMBER_OF_SHOWN_HIGHSCORES && entry != NULL; i++) {
|
||||||
{
|
|
||||||
fprintf(file, "%s;%d\n", entry->name, entry->score);
|
fprintf(file, "%s;%d\n", entry->name, entry->score);
|
||||||
entry = nextTreeData(NULL);
|
entry = nextTreeData(NULL);
|
||||||
}
|
}
|
||||||
@ -127,8 +123,7 @@ void saveHighscores(const char *path)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Free all memory used for highscores.
|
// Free all memory used for highscores.
|
||||||
void clearHighscores()
|
void clearHighscores() {
|
||||||
{
|
clearTree(&highscoreTree);
|
||||||
clearTree(highscoreTree);
|
|
||||||
highscoreTree = NULL;
|
highscoreTree = NULL;
|
||||||
}
|
}
|
||||||
@ -1,10 +1,10 @@
|
|||||||
Kristin;9944
|
Kristin;49209
|
||||||
Kristin;7947
|
krisp;29797
|
||||||
Kristin;6962
|
krisp;29792
|
||||||
Kristin;5987
|
Kristin;29782
|
||||||
Kristin;5975
|
Kristin;19943
|
||||||
krisp;4986
|
krisp;19934
|
||||||
krisp;4985
|
krisp;19916
|
||||||
Kristin;4972
|
kristin;19861
|
||||||
player1;3999
|
Kristin;19858
|
||||||
Kristin;3992
|
p;19729
|
||||||
|
|||||||
52
main.c
52
main.c
@ -1,30 +1,28 @@
|
|||||||
#include <stdlib.h>
|
#include "highscore.h"
|
||||||
#include <stdio.h>
|
|
||||||
#include "numbers.h"
|
#include "numbers.h"
|
||||||
#include "timer.h"
|
#include "timer.h"
|
||||||
#include "highscore.h"
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <time.h>
|
||||||
|
|
||||||
// Read an unsigned integer from stdin with prompt (retries until valid).
|
// Read an unsigned integer from stdin with prompt (retries until valid).
|
||||||
int inputNumber(const char *promptText)
|
int inputNumber(const char *promptText) {
|
||||||
{
|
|
||||||
unsigned int number;
|
unsigned int number;
|
||||||
int numberOfInputs = 0;
|
int numberOfInputs = 0;
|
||||||
|
|
||||||
while(numberOfInputs != 1)
|
while (numberOfInputs != 1) {
|
||||||
{
|
|
||||||
printf("%s", promptText);
|
printf("%s", promptText);
|
||||||
numberOfInputs = scanf("%u", &number);
|
numberOfInputs = scanf("%u", &number);
|
||||||
while(getchar() != '\n') {} // clear input buffer
|
while (getchar() != '\n') {
|
||||||
|
} // clear input buffer
|
||||||
}
|
}
|
||||||
|
|
||||||
return number;
|
return number;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Print an array of numbers.
|
// Print an array of numbers.
|
||||||
void showNumbers(const unsigned int *numbers, unsigned int len)
|
void showNumbers(const unsigned int *numbers, unsigned int len) {
|
||||||
{
|
if (numbers != NULL) {
|
||||||
if(numbers != NULL)
|
|
||||||
{
|
|
||||||
printf("Numbers:");
|
printf("Numbers:");
|
||||||
|
|
||||||
for (int i = 0; i < len; i++)
|
for (int i = 0; i < len; i++)
|
||||||
@ -34,18 +32,16 @@ void showNumbers(const unsigned int *numbers, unsigned int len)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Main game loop: generate numbers, ask user for duplicate, measure time, update highscores.
|
// Main game loop: generate numbers, ask user for duplicate, measure time,
|
||||||
int main(int argc, char *argv[])
|
// update highscores.
|
||||||
{
|
int main(int argc, char *argv[]) {
|
||||||
|
srand(time(NULL)); // seed für srand
|
||||||
int exitCode = EXIT_FAILURE;
|
int exitCode = EXIT_FAILURE;
|
||||||
|
|
||||||
if(argc != 2)
|
if (argc != 2) {
|
||||||
{
|
|
||||||
fprintf(stderr, "Usage: %s <player name>\n", argv[0]);
|
fprintf(stderr, "Usage: %s <player name>\n", argv[0]);
|
||||||
exitCode = EXIT_FAILURE;
|
exitCode = EXIT_FAILURE;
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
const char *highscorePath = "highscores.txt";
|
const char *highscorePath = "highscores.txt";
|
||||||
const char *playerName = argv[1];
|
const char *playerName = argv[1];
|
||||||
unsigned int *numbers = NULL;
|
unsigned int *numbers = NULL;
|
||||||
@ -56,7 +52,8 @@ int main(int argc, char *argv[])
|
|||||||
|
|
||||||
// ask until valid number of elements (3..1000)
|
// ask until valid number of elements (3..1000)
|
||||||
while (numberOfElements < 3 || numberOfElements > 1000)
|
while (numberOfElements < 3 || numberOfElements > 1000)
|
||||||
numberOfElements = inputNumber("Wie viele Zahlen sollen gezeigt werden: ");
|
numberOfElements =
|
||||||
|
inputNumber("Wie viele Zahlen sollen gezeigt werden: ");
|
||||||
|
|
||||||
// create numbers and show them
|
// create numbers and show them
|
||||||
numbers = createNumbers(numberOfElements);
|
numbers = createNumbers(numberOfElements);
|
||||||
@ -70,13 +67,14 @@ int main(int argc, char *argv[])
|
|||||||
duplicate = getDuplicate(numbers, numberOfElements);
|
duplicate = getDuplicate(numbers, numberOfElements);
|
||||||
|
|
||||||
// check result and update highscores
|
// check result and update highscores
|
||||||
if(userInput == duplicate)
|
if (userInput == duplicate) {
|
||||||
{
|
|
||||||
int score = addHighscore(playerName, measuredSeconds, numberOfElements);
|
int score = addHighscore(playerName, measuredSeconds, numberOfElements);
|
||||||
printf("Sie haben die korrekte Zahl in %.6lf Sekunde(n) gefunden und %u Punkte erzielt.\n", measuredSeconds, score);
|
printf("Sie haben die korrekte Zahl in %.6lf Sekunde(n) gefunden und %u "
|
||||||
}
|
"Punkte erzielt.\n",
|
||||||
else
|
measuredSeconds, score);
|
||||||
printf("Leider ist %u nicht korrekt. Richtig waere %u gewesen.\n", userInput, duplicate);
|
} else
|
||||||
|
printf("Leider ist %u nicht korrekt. Richtig waere %u gewesen.\n",
|
||||||
|
userInput, duplicate);
|
||||||
|
|
||||||
loadHighscores(highscorePath);
|
loadHighscores(highscorePath);
|
||||||
showHighscores();
|
showHighscores();
|
||||||
|
|||||||
120
numbers.c
120
numbers.c
@ -3,19 +3,6 @@
|
|||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <time.h>
|
|
||||||
|
|
||||||
//Vergleicht
|
|
||||||
int compareUnsignedInt(const void *a, const void *b) {
|
|
||||||
unsigned int x = *(unsigned int *)a;
|
|
||||||
unsigned int y = *(unsigned int *)b;
|
|
||||||
|
|
||||||
if (x < y)
|
|
||||||
return -1;
|
|
||||||
if (x > y)
|
|
||||||
return 1;
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO: getDuplicate und createNumbers implementieren
|
// TODO: getDuplicate und createNumbers implementieren
|
||||||
/**Erzeugen eines Arrays mit der vom Nutzer eingegebenen Anzahl an
|
/**Erzeugen eines Arrays mit der vom Nutzer eingegebenen Anzahl an
|
||||||
@ -28,65 +15,82 @@ int compareUnsignedInt(const void *a, const void *b) {
|
|||||||
// different, except for two entries. Returns NULL on errors. Use your
|
// different, except for two entries. Returns NULL on errors. Use your
|
||||||
// implementation of the binary search tree to check for possible duplicates
|
// implementation of the binary search tree to check for possible duplicates
|
||||||
// while creating random numbers.
|
// while creating random numbers.
|
||||||
unsigned int *createNumbers(unsigned int len) {
|
|
||||||
if (len < 2)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
unsigned int *arr = malloc(sizeof(unsigned int) * len);
|
// vergleicht zwei Werte: a<b: -1 a>b: 1 a=b: 0
|
||||||
if (!arr)
|
int compareUnsignedInt(const void *a, const void *b) {
|
||||||
return NULL;
|
unsigned int x = *(unsigned int *)a;
|
||||||
|
unsigned int y = *(unsigned int *)b;
|
||||||
TreeNode *root = NULL;
|
return (x < y) ? -1 : (x > y);
|
||||||
srand((unsigned int)time(NULL));
|
|
||||||
|
|
||||||
for (unsigned int i = 0; i < len - 1; i++) {
|
|
||||||
unsigned int num;
|
|
||||||
int isDuplicate;
|
|
||||||
|
|
||||||
do {
|
|
||||||
num = (rand() % (2 * len)) + 1;
|
|
||||||
isDuplicate = 0;
|
|
||||||
|
|
||||||
root = addToTree(root, &num, sizeof(unsigned int), compareUnsignedInt,
|
|
||||||
&isDuplicate);
|
|
||||||
|
|
||||||
} while (isDuplicate); // nur akzeptieren, wenn eindeutig
|
|
||||||
|
|
||||||
arr[i] = num;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Jetzt gezielt EIN Duplikat erzeugen
|
unsigned int *createNumbers(unsigned int len) {
|
||||||
unsigned int duplicateIndex = rand() % (len - 1);
|
if (len < 2) // Duplikat bei zwei Einträgen sinnlos
|
||||||
arr[len - 1] = arr[duplicateIndex];
|
return NULL;
|
||||||
|
|
||||||
clearTree(root);
|
unsigned int *numbersArray = malloc(
|
||||||
return arr;
|
sizeof(unsigned int) * len); // Speicher für das Ausgabearray reservieren:
|
||||||
|
// Größe eines Eintrags * Größe des Arrays
|
||||||
|
if (!numbersArray) // Speicher konnte nicht reserviert werden
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
TreeNode *root =
|
||||||
|
NULL; // Binärbaum zum Generieren der Zufallszahlen ohne Duplikate
|
||||||
|
|
||||||
|
for (unsigned int i = 0; i < len; i++) {
|
||||||
|
unsigned int currentNumber;
|
||||||
|
int isDuplicate;
|
||||||
|
do { // mindestens eine Zufallszahl erzeugen
|
||||||
|
currentNumber = (rand() % (2 * len)) + 1; // Zahlenbereich 1 bis 2*len
|
||||||
|
isDuplicate = 0;
|
||||||
|
root = addToTree(root, ¤tNumber, sizeof(unsigned int),
|
||||||
|
compareUnsignedInt,
|
||||||
|
&isDuplicate); // compareUnsignedInt wird zum Verwenden
|
||||||
|
// bei Vergleichen übergeben
|
||||||
|
} while (isDuplicate); // wenn isDuplicate gesetzt wird, muss eine neue Zahl
|
||||||
|
// erzeugt werden, die Schleife wird wiederholt
|
||||||
|
numbersArray[i] = currentNumber;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Ein zufälliges Duplikat erzeugen
|
||||||
|
unsigned int duplicateIndex =
|
||||||
|
rand() % len; // Index des Duplikats per Zufall bestimmen
|
||||||
|
unsigned int newIndex;
|
||||||
|
do {
|
||||||
|
newIndex = rand() % len;
|
||||||
|
} while (newIndex == duplicateIndex); // zweiten Index bestimmen, der nicht
|
||||||
|
// mit dem ersten übereinstimmt
|
||||||
|
|
||||||
|
numbersArray[newIndex] =
|
||||||
|
numbersArray[duplicateIndex]; // Wert vom ersten Index kopieren
|
||||||
|
|
||||||
|
clearTree(&root); // Speicher wieder freigeben, wird nicht mehr benötigt
|
||||||
|
return numbersArray;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns only the only number in numbers which is present twice. Returns zero
|
// Returns only the only number in numbers which is present twice. Returns zero
|
||||||
// on errors.
|
// on errors.
|
||||||
unsigned int getDuplicate(const unsigned int *numbers, unsigned int len) {
|
unsigned int getDuplicate(
|
||||||
|
const unsigned int *numbers,
|
||||||
|
unsigned int len) { // array numbers, sowie die Länge wird übergeben
|
||||||
if (!numbers || len < 2)
|
if (!numbers || len < 2)
|
||||||
return 0;
|
return 0; // fehlerhaftes Array
|
||||||
|
|
||||||
unsigned int *copy = malloc(sizeof(unsigned int) * len);
|
TreeNode *root = NULL; // leerer Baum
|
||||||
if (!copy)
|
unsigned int duplicateValue = 0; // Wert des Duplikats
|
||||||
return 0;
|
|
||||||
|
|
||||||
memcpy(copy, numbers, sizeof(unsigned int) * len);
|
for (unsigned int i = 0; i < len && duplicateValue == 0; i++) { // Schleife
|
||||||
|
int isDuplicate = 0;
|
||||||
|
|
||||||
// Sortierung
|
// Zahl in den Baum einfügen
|
||||||
qsort(copy, len, sizeof(unsigned int), compareUnsignedInt);
|
root = addToTree(root, &numbers[i], sizeof(unsigned int),
|
||||||
|
compareUnsignedInt, &isDuplicate);
|
||||||
|
|
||||||
// Duplikat finden: zwei gleiche nebeneinander
|
// Duplikat erkannt
|
||||||
unsigned int duplicate = 0;
|
if (isDuplicate && duplicateValue == 0) {
|
||||||
for (unsigned int i = 0; i < len - 1; i++) {
|
duplicateValue = numbers[i]; // Duplikat merken, for-Schleife wird beendet
|
||||||
if (copy[i] == copy[i + 1]) {
|
|
||||||
duplicate = copy[i];
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
free(copy);
|
clearTree(&root); // Baum freigeben
|
||||||
return duplicate;
|
return duplicateValue; // 0, falls kein Duplikat
|
||||||
}
|
}
|
||||||
|
|||||||
10
numbers.h
10
numbers.h
@ -3,12 +3,14 @@
|
|||||||
|
|
||||||
int compareUnsignedInt(const void *a, const void *b);
|
int compareUnsignedInt(const void *a, const void *b);
|
||||||
|
|
||||||
// Returns len random numbers between 1 and 2x len in random order which are all different, except for two entries.
|
// Returns len random numbers between 1 and 2x len in random order which are all
|
||||||
// Returns NULL on errors. Use your implementation of the binary search tree to check for possible duplicates while
|
// different, except for two entries. Returns NULL on errors. Use your
|
||||||
// creating random numbers.
|
// implementation of the binary search tree to check for possible duplicates
|
||||||
|
// while creating random numbers.
|
||||||
unsigned int *createNumbers(unsigned int len);
|
unsigned int *createNumbers(unsigned int len);
|
||||||
|
|
||||||
// Returns only the only number in numbers which is present twice. Returns zero on errors.
|
// Returns only the only number in numbers which is present twice. Returns zero
|
||||||
|
// on errors.
|
||||||
unsigned int getDuplicate(const unsigned int *numbers, unsigned int len);
|
unsigned int getDuplicate(const unsigned int *numbers, unsigned int len);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
@ -4,6 +4,7 @@
|
|||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
#include "bintree.h"
|
#include "bintree.h"
|
||||||
|
|
||||||
int compareUnsignedInt(const void *a, const void *b) {
|
int compareUnsignedInt(const void *a, const void *b) {
|
||||||
unsigned int x = *(unsigned int *)a;
|
unsigned int x = *(unsigned int *)a;
|
||||||
unsigned int y = *(unsigned int *)b;
|
unsigned int y = *(unsigned int *)b;
|
||||||
@ -21,71 +22,91 @@ void setUp(void) {
|
|||||||
root = NULL; // vor jedem Test leeren
|
root = NULL; // vor jedem Test leeren
|
||||||
}
|
}
|
||||||
|
|
||||||
void tearDown(void) { clearTree(root); }
|
void tearDown(void) { clearTree(&root); }
|
||||||
|
|
||||||
// Test, ob addToTree Knoten korrekt hinzufügt
|
// Test, ob addToTree Knoten korrekt hinzufügt
|
||||||
|
|
||||||
|
/*TreeNode *addToTree(TreeNode *root, const void *data, size_t dataSize,
|
||||||
|
CompareFctType compareFct, int *isDuplicate) */
|
||||||
void test_addToTree_basic(void) {
|
void test_addToTree_basic(void) {
|
||||||
int isDup;
|
int isDuplicate;
|
||||||
unsigned int val = 10;
|
unsigned int testInt = 10;
|
||||||
root = addToTree(root, &val, sizeof(val), compareUnsignedInt, &isDup);
|
root = addToTree(root, &testInt, sizeof(testInt), compareUnsignedInt,
|
||||||
TEST_ASSERT_NOT_NULL(root);
|
&isDuplicate);
|
||||||
TEST_ASSERT_EQUAL_UINT(10, *(unsigned int *)root->data);
|
TEST_ASSERT_NOT_NULL(root); // Knoten wurde erfolgreich erzeugt
|
||||||
TEST_ASSERT_EQUAL_INT(0, isDup);
|
TEST_ASSERT_EQUAL_UINT(
|
||||||
TEST_ASSERT_EQUAL_UINT(1, treeSize(root));
|
10,
|
||||||
|
*(unsigned int *)root
|
||||||
|
->data); // Datenzeiger wurde richtig gesetzt, void pointer auf
|
||||||
|
// unsigned int pointer casten, mit *wird der Wert abgerufen
|
||||||
|
TEST_ASSERT_EQUAL_INT(0, isDuplicate); // kein Duplikat
|
||||||
|
TEST_ASSERT_EQUAL_UINT(1, treeSize(root)); // der tree hat einen Eintrag
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test, dass Duplikate erkannt werden
|
// Test, dass Duplikate erkannt werden
|
||||||
void test_addToTree_duplicate(void) {
|
void test_addToTree_duplicate(void) {
|
||||||
int isDup;
|
int isDuplicate;
|
||||||
unsigned int val1 = 10, val2 = 10;
|
unsigned int val1 = 10, val2 = 10; // Duplikate
|
||||||
root = addToTree(root, &val1, sizeof(val1), compareUnsignedInt, &isDup);
|
root = addToTree(root, &val1, sizeof(val1), compareUnsignedInt,
|
||||||
TEST_ASSERT_EQUAL_INT(0, isDup);
|
&isDuplicate); // val 1 zum leeren Baum hinzufügen
|
||||||
root = addToTree(root, &val2, sizeof(val2), compareUnsignedInt, &isDup);
|
TEST_ASSERT_EQUAL_INT(0, isDuplicate); // erster Knoten->kein Duplikat
|
||||||
TEST_ASSERT_EQUAL_INT(1, isDup);
|
root = addToTree(root, &val2, sizeof(val2), compareUnsignedInt,
|
||||||
TEST_ASSERT_EQUAL_UINT(1, treeSize(root)); // Duplikate nicht hinzufügen
|
&isDuplicate); // val 2 hinzufügen
|
||||||
|
TEST_ASSERT_EQUAL_INT(1, isDuplicate); // Duplikat erkannt
|
||||||
|
TEST_ASSERT_EQUAL_UINT(1,
|
||||||
|
treeSize(root)); // Duplikate wurde nicht hinzugefügt
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test nextTreeData Traversierung
|
// Test nextTreeData Traversierung
|
||||||
void test_nextTreeData_in_order(void) {
|
void test_nextTreeData_in_order(void) {
|
||||||
unsigned int values[] = {20, 10, 30};
|
unsigned int values[] = {20, 10, 30}; // erwartete Ausgabe: 10 -> 20 -> 30
|
||||||
int isDup;
|
int isDuplicate;
|
||||||
for (int i = 0; i < 3; i++) {
|
for (int i = 0; i < 3; i++) {
|
||||||
root = addToTree(root, &values[i], sizeof(values[i]), compareUnsignedInt,
|
root = addToTree(root, &values[i], sizeof(values[i]), compareUnsignedInt,
|
||||||
&isDup);
|
&isDuplicate); // Baum füllen
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned int expected[] = {10, 20, 30};
|
unsigned int expected[] = {10, 20, 30}; // erwartet in Order Reihenfolge
|
||||||
int idx = 0;
|
int valueID = 0;
|
||||||
void *data;
|
void *data;
|
||||||
|
|
||||||
// **Neue Iteration starten**
|
// Neue Iteration starten
|
||||||
data = nextTreeData(root);
|
data = nextTreeData(root);
|
||||||
while (data != NULL) {
|
while (data != NULL) {
|
||||||
TEST_ASSERT_EQUAL_UINT(expected[idx], *(unsigned int *)data);
|
TEST_ASSERT_EQUAL_UINT(expected[valueID],
|
||||||
idx++;
|
*(unsigned int *)data); // entspricht erwartetem Wert
|
||||||
|
|
||||||
|
valueID++;
|
||||||
data = nextTreeData(NULL); // weitere Elemente abrufen
|
data = nextTreeData(NULL); // weitere Elemente abrufen
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST_ASSERT_EQUAL_INT(3, idx); // alle 3 Knoten besucht
|
TEST_ASSERT_EQUAL_INT(3, valueID); // alle 3 Knoten besucht
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test clearTree gibt Speicher frei
|
// Testet, dass clearTree Speicher freigibt und Root auf NULL setzt
|
||||||
void test_clearTree(void) {
|
void test_clearTree_sets_root_null(void) {
|
||||||
unsigned int val = 42;
|
int isDuplicate;
|
||||||
int isDup;
|
unsigned int val1 = 10, val2 = 20;
|
||||||
root = addToTree(root, &val, sizeof(val), compareUnsignedInt, &isDup);
|
|
||||||
clearTree(root);
|
root = addToTree(root, &val1, sizeof(val1), compareUnsignedInt, &isDuplicate);
|
||||||
root = NULL; // clearTree löscht nicht die root-Variable selbst
|
root = addToTree(root, &val2, sizeof(val2), compareUnsignedInt, &isDuplicate);
|
||||||
|
|
||||||
|
// Vor dem Clear prüfen, dass Root nicht NULL ist
|
||||||
|
TEST_ASSERT_NOT_NULL(root);
|
||||||
|
|
||||||
|
clearTree(&root);
|
||||||
|
|
||||||
|
// Nach dem Clear muss Root auf NULL gesetzt sein
|
||||||
TEST_ASSERT_NULL(root);
|
TEST_ASSERT_NULL(root);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Test treeSize zählt korrekt
|
// Test treeSize zählt korrekt
|
||||||
void test_treeSize(void) {
|
void test_treeSize(void) {
|
||||||
unsigned int vals[] = {10, 20, 5};
|
unsigned int testInts[] = {10, 20, 5};
|
||||||
int isDup;
|
int isDuplicate;
|
||||||
for (int i = 0; i < 3; i++) {
|
for (int i = 0; i < 3; i++) {
|
||||||
root =
|
root = addToTree(root, &testInts[i], sizeof(testInts[i]),
|
||||||
addToTree(root, &vals[i], sizeof(vals[i]), compareUnsignedInt, &isDup);
|
compareUnsignedInt, &isDuplicate);
|
||||||
}
|
}
|
||||||
TEST_ASSERT_EQUAL_UINT(3, treeSize(root));
|
TEST_ASSERT_EQUAL_UINT(3, treeSize(root));
|
||||||
}
|
}
|
||||||
@ -99,7 +120,7 @@ int main(void) {
|
|||||||
RUN_TEST(test_addToTree_basic);
|
RUN_TEST(test_addToTree_basic);
|
||||||
RUN_TEST(test_addToTree_duplicate);
|
RUN_TEST(test_addToTree_duplicate);
|
||||||
RUN_TEST(test_nextTreeData_in_order);
|
RUN_TEST(test_nextTreeData_in_order);
|
||||||
RUN_TEST(test_clearTree);
|
RUN_TEST(test_clearTree_sets_root_null);
|
||||||
RUN_TEST(test_treeSize);
|
RUN_TEST(test_treeSize);
|
||||||
return UNITY_END();
|
return UNITY_END();
|
||||||
}
|
}
|
||||||
@ -7,41 +7,52 @@
|
|||||||
|
|
||||||
#define TEST_ARRAY_LEN 100
|
#define TEST_ARRAY_LEN 100
|
||||||
|
|
||||||
void test_createNumbers_length(void) {
|
// Speicher für ein Array wird reserviert
|
||||||
unsigned int *arr = createNumbers(TEST_ARRAY_LEN);
|
void test_createNumbers_length(void) { // erstellt ein Array der Länge hundert
|
||||||
TEST_ASSERT_NOT_NULL(arr);
|
unsigned int *testArray = createNumbers(TEST_ARRAY_LEN);
|
||||||
|
TEST_ASSERT_NOT_NULL(testArray);
|
||||||
free(arr);
|
free(testArray);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Duplikat ist genau einmal vorhanden
|
||||||
void test_createNumbers_single_duplicate(void) {
|
void test_createNumbers_single_duplicate(void) {
|
||||||
unsigned int *arr = createNumbers(TEST_ARRAY_LEN);
|
unsigned int *testArray = createNumbers(TEST_ARRAY_LEN); // Array erstellen
|
||||||
TEST_ASSERT_NOT_NULL(arr);
|
TEST_ASSERT_NOT_NULL(testArray); // Speicher konnte reserviert werden
|
||||||
|
|
||||||
unsigned int duplicate = getDuplicate(arr, TEST_ARRAY_LEN);
|
unsigned int duplicate =
|
||||||
TEST_ASSERT_TRUE(duplicate > 0);
|
getDuplicate(testArray, TEST_ARRAY_LEN); // Duplikat holen
|
||||||
|
TEST_ASSERT_TRUE(duplicate > 0); // Duplikat ist größer als 0
|
||||||
|
TEST_ASSERT_TRUE(
|
||||||
|
duplicate <
|
||||||
|
(2 * TEST_ARRAY_LEN)); // Duplikat liegt im vorgegebenen Zahlenbereich
|
||||||
|
|
||||||
unsigned int count = 0;
|
unsigned int count = 0; // Anzahl der Duplikate
|
||||||
for (unsigned int i = 0; i < TEST_ARRAY_LEN; i++) {
|
for (unsigned int i = 0; i < TEST_ARRAY_LEN;
|
||||||
if (arr[i] == duplicate) {
|
i++) { // Einträge des testArrays auf Duplikate prüfen
|
||||||
|
if (testArray[i] == duplicate) {
|
||||||
count++;
|
count++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TEST_ASSERT_EQUAL_UINT(2, count);
|
TEST_ASSERT_EQUAL_UINT(2, count); // Duplikat zwei mal vorhanden
|
||||||
|
|
||||||
free(arr);
|
free(testArray); // Speicher freigeben
|
||||||
}
|
}
|
||||||
|
|
||||||
void test_getDuplicate_manual_array(void) {
|
// getDuplicate testen
|
||||||
|
void test_getDuplicate_manual_array(
|
||||||
|
void) { // duplikat in fremden array wird gefunden
|
||||||
unsigned int numbers[5] = {10, 20, 30, 40, 20};
|
unsigned int numbers[5] = {10, 20, 30, 40, 20};
|
||||||
unsigned int dup = getDuplicate(numbers, 5);
|
unsigned int duplicate = getDuplicate(numbers, 5);
|
||||||
TEST_ASSERT_EQUAL_UINT(20, dup);
|
TEST_ASSERT_EQUAL_UINT(20, duplicate);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// getDuplicate erkennt fehlerhaftes Array
|
||||||
void test_getDuplicate_invalid_input(void) {
|
void test_getDuplicate_invalid_input(void) {
|
||||||
TEST_ASSERT_EQUAL_UINT(0, getDuplicate(NULL, 5));
|
TEST_ASSERT_EQUAL_UINT(
|
||||||
unsigned int arr[1] = {42};
|
0, getDuplicate(NULL, 5)); // unsigned int getDuplicate(const unsigned int
|
||||||
TEST_ASSERT_EQUAL_UINT(0, getDuplicate(arr, 1));
|
// *numbers, unsigned int len)
|
||||||
|
unsigned int testArray[1] = {2};
|
||||||
|
TEST_ASSERT_EQUAL_UINT(0, getDuplicate(testArray, 1));
|
||||||
}
|
}
|
||||||
|
|
||||||
void setUp(void) {}
|
void setUp(void) {}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user