diff options
Diffstat (limited to 'src/pattern/next.c')
-rw-r--r-- | src/pattern/next.c | 79 |
1 files changed, 79 insertions, 0 deletions
diff --git a/src/pattern/next.c b/src/pattern/next.c new file mode 100644 index 0000000..10261bc --- /dev/null +++ b/src/pattern/next.c @@ -0,0 +1,79 @@ +#include "next.h" +#include <stdlib.h> + +/* + * It gives the first point that: + * - Isn't part of pattern->path + * - Its index the lowest possible, but minimum min_index + * - There isn't any point in-line between it and the last of the path + * Returns true if such a point exsist, otherwise returns false. + */ +bool free_point(struct pattern *pattern, int min_index, struct coord *new_point) +{ + //printf("min_index=%d\n", min_index); + struct coord result = index_to_coord(pattern->type.width, min_index); + struct coord *last = pattern->length > 0 ? &pattern->path[pattern->length - 1] : NULL; + while (result.y < pattern->type.height) + { + while (result.x < pattern->type.width) + { + if (last == NULL) + { + *new_point = result; + return true; + } + else if (find_in_pattern(pattern, &result) < 0 && + nothing_inbetween(pattern, &result)) + { + //printf("fp(%d;%d)\n", result.x, result.y); + *new_point = result; + return true; + } + result.x++; + } + result.y++; + result.x = 0; + } + return false; +} + +/* + * Changes pattern->path to the next possible pattern. + * It returns false if there's no possible pattern left, + * otherwise it returns true. + */ +bool next_point(struct pattern *pattern) +{ + struct coord next_point; + if (len_is_max(pattern)) + { + do + { + if (pattern->length == 0) + return false; //Nincs több minta + next_point = pattern->path[--pattern->length]; + } while (!free_point( + pattern, + coord_to_index(pattern->type.width, next_point) + 1, + &next_point)); + //printf("(%d;%d)\n", next_point.x, next_point.y); + pattern->path[pattern->length++] = next_point; + if (pattern->length >= pattern->type.min_length) + return true; + } + + do + { + if (free_point(pattern, 0, &next_point)) + { + pattern->path[pattern->length++] = next_point; + //return true; + } + } while (pattern->length < pattern->type.min_length); + + return true; + + // Ha visszalépés volt, akkor az első újra előrelépésnél, csak nagyobb indexű + // elemre szabad lépni. + // Ha előrelépés volt, akkor a legkissebb indexű szabad elemre kell lépni. +} |