Skip to content
Snippets Groups Projects
Commit 97a3c65f authored by Manuel Bucher's avatar Manuel Bucher
Browse files

added connection betweent tiles & detect duplicated entry

parent 26e2b52e
Branches
No related merge requests found
all: loesung
WARNINGS = -Wall -Werror
WARNINGS = -Wall #-Werror
OPTIONAL = -Wextra -Wpedantic -Wshadow
DEBUG = -ggdb -fno-omit-frame-pointer
OPTIMIZE = -O3 -std=c11
DEBUG = -g -ggdb -fno-omit-frame-pointer
OPTIMIZE = -O2 -std=c11
loesung: Makefile loesung.c
$(CC) -o $@ $(WARNINGS) $(OPTIONAL) $(DEBUG) $(OPTIMIZE) loesung.c
......
......@@ -7,24 +7,26 @@
typedef struct Tile {
uint32_t x;
uint32_t y;
struct Tile *p_next;
struct Tile *p_prev;
struct Tile *p_n; // north, used for initial list
struct Tile *p_e; // east
struct Tile *p_s; // south
struct Tile *p_w; // west
} Tile;
int tile_compare(const void *p, const void *q) {
const Tile *s = *(const Tile**) p;
const Tile *t = *(const Tile**) q;
// als erstes nach x sortieren
if (s->x < t->x)
return -1;
if (s->x > t->x)
return 1;
// danach nach y sortieren
// als erstes nach y sortieren
if (s->y < t->y)
return -1;
if (s->y > t->y)
return 1;
// danach nach x sortieren
if (s->x < t->x)
return -1;
if (s->x > t->x)
return 1;
return 0; // Elemente sind gleich
}
......@@ -54,24 +56,24 @@ Tile* list_push(List *s) {
}
p_tile->x = 0;
p_tile->y = 0;
p_tile->p_next = s->p_top;
p_tile->p_prev = NULL;
p_tile->p_n = s->p_top;
p_tile->p_e = NULL;
p_tile->p_s = NULL;
p_tile->p_w = NULL;
s->p_top = p_tile;
s->size++;
if(p_tile->p_next != NULL) {
p_tile->p_next->p_prev = p_tile;
}
return p_tile;
}
/** Entfernen des obersten Elementes von der Liste und zurueckgeben des Tiles
*
* Der List muss mindestens ein Element besitzen TODO: Notwendig?
* Der List muss mindestens ein Element besitzen
*/
Tile* list_pop(List *s) {
Tile *p_tile = s->p_top;
s->p_top->p_next = p_tile->p_next;
s->p_top->p_prev = NULL;
s->p_top = s->p_top->p_n;
s->size--;
return p_tile;
}
......@@ -83,7 +85,7 @@ void list_free(List *s) {
Tile *p_cur = s->p_top;
s->p_top = NULL;
while (p_cur != NULL) {
Tile *p_next = p_cur->p_next;
Tile *p_next = p_cur->p_n;
free(p_cur);
p_cur = p_next;
}
......@@ -104,7 +106,9 @@ typedef struct Field {
Tile t_max;
List tile_list;
Tile* (*tile_array);
} Field;
uint32_t num_tiles;
} Field; // TODO: entfernen dieses Structs und nutzen von kleineren Strukturen:
// list + tile_array
/** Parsen einer Kachel(Tile) aus einer Zeile von StdIn
*
......@@ -178,6 +182,7 @@ void field_init(Field *f) {
// initialisieren der Liste
list_init(&f->tile_list);
f->tile_array = 0;
f->num_tiles = 0;
}
/** Freigeben des im Heap reservierten speichers des fields f */
......@@ -252,14 +257,58 @@ MallocResult field_init_tile_array(Field *f) {
return MallocFailed;
}
Tile *cur = f->tile_list.p_top;
f->num_tiles = f->tile_list.size;
for (uint32_t i = 0; i < f->tile_list.size; i++) {
f->tile_array[i] = cur;
cur = cur->p_next;
cur = cur->p_n;
f->tile_array[i]->p_n = NULL;
}
return MallocOk;
}
/** Gruppieren der Felder, setzen der Pointer (north, east, south, west) vom Feld
*
* Voraussetzung: `field_init_tile_array()` muss ausgefuehrt worden sein
* Rueckgabe: 0 falls alles ok
* 1 falls Dopplungen vorkommen TODO: enum
*/
int field_find_neighbours(Field *f) {
uint32_t i = 0; // vergleich mit oberer Zeile
uint32_t begin_line = 0;
for (uint32_t j = 1; j < f->num_tiles; j++) {
Tile *p_cur = f->tile_array[j];
Tile *p_east = f->tile_array[j-1];
// ermitteln der ost/west-Beziehung
if (p_cur->y == p_east->y) {
if (p_cur->x == p_east->x) {
return 1;
}
if (p_cur->x == p_east->x - 1) {
p_cur->p_e = p_east;
p_east->p_w = p_cur;
}
} else {
begin_line = i;
}
// ermitteln der nord/sued-Beziehung
Tile *p_north = f->tile_array[i];
if (p_north->y < p_cur->y - 1) {
i = begin_line; // Luecke zwischen zeilen
} else if (p_north->y == p_cur->y - 1) {
// finden, ob paar existiert, zurzeit O(n).
// TODO: lohnt sich binaere suche mit O(log n)?
for(;f->tile_array[i]->y < p_cur->y && i < begin_line; i++);
p_north = f->tile_array[i];
if (p_north->x == p_cur->x) {
p_north->p_s = p_cur;
p_cur->p_n = p_north;
}
}
}
return 0;
}
void field_print(Field *f) {
printf("# Array\n");
for (uint32_t i = 0; i < f->tile_list.size; i++) {
......@@ -308,6 +357,16 @@ int main (void)
}
qsort(field.tile_array, field.tile_list.size, sizeof(Tile*), tile_compare);
if(field_find_neighbours(&field)) {
fprintf(stderr, "Error: Duplicated entry\n");
return EXIT_FAILURE;
}
//field_print(&field);
// TODO: Untertilesets finden
// TODO: Problem fuer die Untertilesets loesen
// TODO: Loesung ausgeben
field_drop(&field);
return EXIT_SUCCESS;
}
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment