diff options
Diffstat (limited to 'apps/plugins/puzzles/src/latin.c')
-rw-r--r-- | apps/plugins/puzzles/src/latin.c | 39 |
1 files changed, 26 insertions, 13 deletions
diff --git a/apps/plugins/puzzles/src/latin.c b/apps/plugins/puzzles/src/latin.c index 9d06ccd938..39930166e7 100644 --- a/apps/plugins/puzzles/src/latin.c +++ b/apps/plugins/puzzles/src/latin.c | |||
@@ -19,8 +19,8 @@ | |||
19 | static int latin_solver_top(struct latin_solver *solver, int maxdiff, | 19 | static int latin_solver_top(struct latin_solver *solver, int maxdiff, |
20 | int diff_simple, int diff_set_0, int diff_set_1, | 20 | int diff_simple, int diff_set_0, int diff_set_1, |
21 | int diff_forcing, int diff_recursive, | 21 | int diff_forcing, int diff_recursive, |
22 | usersolver_t const *usersolvers, void *ctx, | 22 | usersolver_t const *usersolvers, validator_t valid, |
23 | ctxnew_t ctxnew, ctxfree_t ctxfree); | 23 | void *ctx, ctxnew_t ctxnew, ctxfree_t ctxfree); |
24 | 24 | ||
25 | #ifdef STANDALONE_SOLVER | 25 | #ifdef STANDALONE_SOLVER |
26 | int solver_show_working, solver_recurse_depth; | 26 | int solver_show_working, solver_recurse_depth; |
@@ -711,7 +711,7 @@ int latin_solver_diff_set(struct latin_solver *solver, | |||
711 | static int latin_solver_recurse | 711 | static int latin_solver_recurse |
712 | (struct latin_solver *solver, int diff_simple, int diff_set_0, | 712 | (struct latin_solver *solver, int diff_simple, int diff_set_0, |
713 | int diff_set_1, int diff_forcing, int diff_recursive, | 713 | int diff_set_1, int diff_forcing, int diff_recursive, |
714 | usersolver_t const *usersolvers, void *ctx, | 714 | usersolver_t const *usersolvers, validator_t valid, void *ctx, |
715 | ctxnew_t ctxnew, ctxfree_t ctxfree) | 715 | ctxnew_t ctxnew, ctxfree_t ctxfree) |
716 | { | 716 | { |
717 | int best, bestcount; | 717 | int best, bestcount; |
@@ -817,7 +817,8 @@ static int latin_solver_recurse | |||
817 | ret = latin_solver_top(&subsolver, diff_recursive, | 817 | ret = latin_solver_top(&subsolver, diff_recursive, |
818 | diff_simple, diff_set_0, diff_set_1, | 818 | diff_simple, diff_set_0, diff_set_1, |
819 | diff_forcing, diff_recursive, | 819 | diff_forcing, diff_recursive, |
820 | usersolvers, newctx, ctxnew, ctxfree); | 820 | usersolvers, valid, newctx, |
821 | ctxnew, ctxfree); | ||
821 | latin_solver_free(&subsolver); | 822 | latin_solver_free(&subsolver); |
822 | if (ctxnew) | 823 | if (ctxnew) |
823 | ctxfree(newctx); | 824 | ctxfree(newctx); |
@@ -879,8 +880,8 @@ static int latin_solver_recurse | |||
879 | static int latin_solver_top(struct latin_solver *solver, int maxdiff, | 880 | static int latin_solver_top(struct latin_solver *solver, int maxdiff, |
880 | int diff_simple, int diff_set_0, int diff_set_1, | 881 | int diff_simple, int diff_set_0, int diff_set_1, |
881 | int diff_forcing, int diff_recursive, | 882 | int diff_forcing, int diff_recursive, |
882 | usersolver_t const *usersolvers, void *ctx, | 883 | usersolver_t const *usersolvers, validator_t valid, |
883 | ctxnew_t ctxnew, ctxfree_t ctxfree) | 884 | void *ctx, ctxnew_t ctxnew, ctxfree_t ctxfree) |
884 | { | 885 | { |
885 | struct latin_solver_scratch *scratch = latin_solver_new_scratch(solver); | 886 | struct latin_solver_scratch *scratch = latin_solver_new_scratch(solver); |
886 | int ret, diff = diff_simple; | 887 | int ret, diff = diff_simple; |
@@ -941,7 +942,8 @@ static int latin_solver_top(struct latin_solver *solver, int maxdiff, | |||
941 | int nsol = latin_solver_recurse(solver, | 942 | int nsol = latin_solver_recurse(solver, |
942 | diff_simple, diff_set_0, diff_set_1, | 943 | diff_simple, diff_set_0, diff_set_1, |
943 | diff_forcing, diff_recursive, | 944 | diff_forcing, diff_recursive, |
944 | usersolvers, ctx, ctxnew, ctxfree); | 945 | usersolvers, valid, ctx, |
946 | ctxnew, ctxfree); | ||
945 | if (nsol < 0) diff = diff_impossible; | 947 | if (nsol < 0) diff = diff_impossible; |
946 | else if (nsol == 1) diff = diff_recursive; | 948 | else if (nsol == 1) diff = diff_recursive; |
947 | else if (nsol > 1) diff = diff_ambiguous; | 949 | else if (nsol > 1) diff = diff_ambiguous; |
@@ -990,6 +992,17 @@ static int latin_solver_top(struct latin_solver *solver, int maxdiff, | |||
990 | } | 992 | } |
991 | #endif | 993 | #endif |
992 | 994 | ||
995 | if (diff != diff_impossible && diff != diff_unfinished && | ||
996 | diff != diff_ambiguous && valid && !valid(solver, ctx)) { | ||
997 | #ifdef STANDALONE_SOLVER | ||
998 | if (solver_show_working) { | ||
999 | printf("%*ssolution failed final validation!\n", | ||
1000 | solver_recurse_depth*4, ""); | ||
1001 | } | ||
1002 | #endif | ||
1003 | diff = diff_impossible; | ||
1004 | } | ||
1005 | |||
993 | latin_solver_free_scratch(scratch); | 1006 | latin_solver_free_scratch(scratch); |
994 | 1007 | ||
995 | return diff; | 1008 | return diff; |
@@ -998,8 +1011,8 @@ static int latin_solver_top(struct latin_solver *solver, int maxdiff, | |||
998 | int latin_solver_main(struct latin_solver *solver, int maxdiff, | 1011 | int latin_solver_main(struct latin_solver *solver, int maxdiff, |
999 | int diff_simple, int diff_set_0, int diff_set_1, | 1012 | int diff_simple, int diff_set_0, int diff_set_1, |
1000 | int diff_forcing, int diff_recursive, | 1013 | int diff_forcing, int diff_recursive, |
1001 | usersolver_t const *usersolvers, void *ctx, | 1014 | usersolver_t const *usersolvers, validator_t valid, |
1002 | ctxnew_t ctxnew, ctxfree_t ctxfree) | 1015 | void *ctx, ctxnew_t ctxnew, ctxfree_t ctxfree) |
1003 | { | 1016 | { |
1004 | int diff; | 1017 | int diff; |
1005 | #ifdef STANDALONE_SOLVER | 1018 | #ifdef STANDALONE_SOLVER |
@@ -1027,7 +1040,7 @@ int latin_solver_main(struct latin_solver *solver, int maxdiff, | |||
1027 | diff = latin_solver_top(solver, maxdiff, | 1040 | diff = latin_solver_top(solver, maxdiff, |
1028 | diff_simple, diff_set_0, diff_set_1, | 1041 | diff_simple, diff_set_0, diff_set_1, |
1029 | diff_forcing, diff_recursive, | 1042 | diff_forcing, diff_recursive, |
1030 | usersolvers, ctx, ctxnew, ctxfree); | 1043 | usersolvers, valid, ctx, ctxnew, ctxfree); |
1031 | 1044 | ||
1032 | #ifdef STANDALONE_SOLVER | 1045 | #ifdef STANDALONE_SOLVER |
1033 | sfree(names); | 1046 | sfree(names); |
@@ -1040,8 +1053,8 @@ int latin_solver_main(struct latin_solver *solver, int maxdiff, | |||
1040 | int latin_solver(digit *grid, int o, int maxdiff, | 1053 | int latin_solver(digit *grid, int o, int maxdiff, |
1041 | int diff_simple, int diff_set_0, int diff_set_1, | 1054 | int diff_simple, int diff_set_0, int diff_set_1, |
1042 | int diff_forcing, int diff_recursive, | 1055 | int diff_forcing, int diff_recursive, |
1043 | usersolver_t const *usersolvers, void *ctx, | 1056 | usersolver_t const *usersolvers, validator_t valid, |
1044 | ctxnew_t ctxnew, ctxfree_t ctxfree) | 1057 | void *ctx, ctxnew_t ctxnew, ctxfree_t ctxfree) |
1045 | { | 1058 | { |
1046 | struct latin_solver solver; | 1059 | struct latin_solver solver; |
1047 | int diff; | 1060 | int diff; |
@@ -1050,7 +1063,7 @@ int latin_solver(digit *grid, int o, int maxdiff, | |||
1050 | diff = latin_solver_main(&solver, maxdiff, | 1063 | diff = latin_solver_main(&solver, maxdiff, |
1051 | diff_simple, diff_set_0, diff_set_1, | 1064 | diff_simple, diff_set_0, diff_set_1, |
1052 | diff_forcing, diff_recursive, | 1065 | diff_forcing, diff_recursive, |
1053 | usersolvers, ctx, ctxnew, ctxfree); | 1066 | usersolvers, valid, ctx, ctxnew, ctxfree); |
1054 | latin_solver_free(&solver); | 1067 | latin_solver_free(&solver); |
1055 | return diff; | 1068 | return diff; |
1056 | } | 1069 | } |