aboutsummaryrefslogtreecommitdiff
path: root/src/solvers/h48/solve.h
diff options
context:
space:
mode:
authorSebastiano Tronto <sebastiano@tronto.net>2024-12-15 10:50:00 +0100
committerSebastiano Tronto <sebastiano@tronto.net>2024-12-15 10:50:00 +0100
commitcb800102a14fb6923546b9d036dbf4e6a5b7542a (patch)
treef0764cd8a1f0681cdb9492cf445d60d56c8304d3 /src/solvers/h48/solve.h
parentd2eb169c675101a64fb873a289fad1d4fe70c5e5 (diff)
downloadnissy-core-cb800102a14fb6923546b9d036dbf4e6a5b7542a.tar.gz
nissy-core-cb800102a14fb6923546b9d036dbf4e6a5b7542a.zip
Solve bug related to duplicate solutions
Diffstat (limited to 'src/solvers/h48/solve.h')
-rw-r--r--src/solvers/h48/solve.h94
1 files changed, 54 insertions, 40 deletions
diff --git a/src/solvers/h48/solve.h b/src/solvers/h48/solve.h
index 1ca294a..d168985 100644
--- a/src/solvers/h48/solve.h
+++ b/src/solvers/h48/solve.h
@@ -57,8 +57,7 @@ typedef struct {
57} dfsarg_solve_h48_maketasks_t; 57} dfsarg_solve_h48_maketasks_t;
58 58
59STATIC int64_t solve_h48_appendsolution(dfsarg_solve_h48_t *); 59STATIC int64_t solve_h48_appendsolution(dfsarg_solve_h48_t *);
60STATIC bool solve_h48_appendmoves(dfsarg_solve_h48_t *, int8_t, 60STATIC int64_t solve_h48_appendallsym(dfsarg_solve_h48_t *);
61 uint8_t *, uint8_t);
62STATIC bool solve_h48_appendchar(dfsarg_solve_h48_t *, char); 61STATIC bool solve_h48_appendchar(dfsarg_solve_h48_t *, char);
63STATIC_INLINE bool solve_h48_stop(dfsarg_solve_h48_t *); 62STATIC_INLINE bool solve_h48_stop(dfsarg_solve_h48_t *);
64STATIC int64_t solve_h48_maketasks( 63STATIC int64_t solve_h48_maketasks(
@@ -73,15 +72,10 @@ STATIC int64_t solve_h48(cube_t, int8_t, int8_t, uint64_t, int8_t, int8_t,
73STATIC int64_t 72STATIC int64_t
74solve_h48_appendsolution(dfsarg_solve_h48_t *arg) 73solve_h48_appendsolution(dfsarg_solve_h48_t *arg)
75{ 74{
76 uint8_t t;
77 int64_t ret;
78 uint64_t solstart;
79
80 if (*arg->nsols >= arg->maxsolutions || 75 if (*arg->nsols >= arg->maxsolutions ||
81 arg->nmoves + arg->npremoves > *arg->shortest_sol + arg->optimal) 76 arg->nmoves + arg->npremoves > *arg->shortest_sol + arg->optimal)
82 return 0; 77 return 0;
83 78
84 solstart = *arg->solutions_used;
85 invertmoves(arg->premoves, arg->npremoves, arg->moves + arg->nmoves); 79 invertmoves(arg->premoves, arg->npremoves, arg->moves + arg->nmoves);
86 80
87 /* Do not append the solution in case premoves cancel with normal */ 81 /* Do not append the solution in case premoves cancel with normal */
@@ -90,18 +84,63 @@ solve_h48_appendsolution(dfsarg_solve_h48_t *arg)
90 if (arg->npremoves > 1 && !allowednextmove(arg->moves, arg->nmoves+2)) 84 if (arg->npremoves > 1 && !allowednextmove(arg->moves, arg->nmoves+2))
91 return 0; 85 return 0;
92 86
93 for (t = 0, ret = 0; t < 48 && *arg->nsols < arg->maxsolutions; t++) { 87 return solve_h48_appendallsym(arg);
88}
89
90STATIC int64_t
91solve_h48_appendallsym(dfsarg_solve_h48_t *arg)
92{
93 bool eq;
94 uint8_t t, i, j, k, n;
95 int64_t ret, strl, l;
96 char *m;
97 uint8_t all[NTRANS][MAXLEN];
98
99 n = arg->nmoves + arg->npremoves;
100
101 for (t = 0, j = 0; t < NTRANS; t++) {
94 if (!(arg->symmask0 & (UINT64_C(1) << (uint64_t)t))) 102 if (!(arg->symmask0 & (UINT64_C(1) << (uint64_t)t)))
95 continue; 103 continue;
96 104
97 if (!solve_h48_appendmoves(arg, arg->nmoves + arg->npremoves, 105 for (i = 0; i < n; i++)
98 arg->moves, t)) 106 all[j][i] = transform_move(arg->moves[i], t);
99 goto solve_h48_appendsolution_error; 107
108 /* Sort parallel moves for consistency */
109 for (i = 0; i < n - 1; i++)
110 if (moveaxis(all[j][i]) == moveaxis(all[j][i+1]) &&
111 movebase(all[j][i]) == movebase(all[j][i+1]) + 1)
112 SWAP(all[j][i], all[j][i+1]);
113
114 /* Check for duplicate solutions */
115 for (k = 0; k < j; k++) {
116 eq = true;
117 for (i = 0; i < n; i++)
118 if (all[k][i] != all[j][i])
119 eq = false;
120 /* If a solution was already found, we skip it */
121 if (eq)
122 continue;
123 }
124
125 /* If all is good, the solution is accepted */
126 j++;
127 }
128
129 /* The solutions are appended */
130 for (k = 0; k < j && *arg->nsols < arg->maxsolutions; k++) {
131 l = arg->solutions_size - *arg->solutions_used;
132 m = *arg->solutions + *arg->solutions_used;
133 strl = writemoves(all[k], n, l, m);
134 if (strl < 0)
135 goto solve_h48_appendallsym_error;
100 136
101 LOG("Solution found: %s\n", *arg->solutions + solstart); 137 LOG("Solution found: %s\n", m);
138
139 *arg->solutions_used += MAX(0, strl-1);
102 140
103 if (!solve_h48_appendchar(arg, '\n')) 141 if (!solve_h48_appendchar(arg, '\n'))
104 goto solve_h48_appendsolution_error; 142 goto solve_h48_appendallsym_error;
143
105 (*arg->nsols)++; 144 (*arg->nsols)++;
106 *arg->shortest_sol = 145 *arg->shortest_sol =
107 MIN(*arg->shortest_sol, arg->nmoves + arg->npremoves); 146 MIN(*arg->shortest_sol, arg->nmoves + arg->npremoves);
@@ -110,37 +149,12 @@ solve_h48_appendsolution(dfsarg_solve_h48_t *arg)
110 149
111 return ret; 150 return ret;
112 151
113solve_h48_appendsolution_error: 152solve_h48_appendallsym_error:
114 LOG("Could not append solution to buffer: size too small\n"); 153 LOG("Could not append solution to buffer: size too small\n");
115 return NISSY_ERROR_BUFFER_SIZE; 154 return NISSY_ERROR_BUFFER_SIZE;
116} 155}
117 156
118STATIC bool 157STATIC bool
119solve_h48_appendmoves(
120 dfsarg_solve_h48_t *arg,
121 int8_t n,
122 uint8_t *moves,
123 uint8_t t
124)
125{
126 int i;
127 int64_t strl;
128 uint8_t mm[MAXLEN];
129
130 for (i = 0; i < n; i++)
131 mm[i] = transform_move(moves[i], t);
132
133 strl = writemoves(mm, n, arg->solutions_size - *arg->solutions_used,
134 *arg->solutions + *arg->solutions_used);
135
136 if (strl < 0)
137 return false;
138
139 *arg->solutions_used += MAX(0, strl-1);
140 return true;
141}
142
143STATIC bool
144solve_h48_appendchar(dfsarg_solve_h48_t *arg, char c) 158solve_h48_appendchar(dfsarg_solve_h48_t *arg, char c)
145{ 159{
146 if (arg->solutions_size <= *arg->solutions_used) 160 if (arg->solutions_size <= *arg->solutions_used)
@@ -397,7 +411,7 @@ solve_h48_maketasks(
397 411
398 /* Avoid symmetry-equivalent moves from the starting cube */ 412 /* Avoid symmetry-equivalent moves from the starting cube */
399 if (maketasks_arg->nmoves == 1) 413 if (maketasks_arg->nmoves == 1)
400 for (t = 0; t < 48; t++) 414 for (t = 0; t < NTRANS; t++)
401 if (solve_arg->symmask0 & 415 if (solve_arg->symmask0 &
402 (UINT64_C(1) << (uint64_t)t)) 416 (UINT64_C(1) << (uint64_t)t))
403 mm &= ~(UINT32_C(1) << 417 mm &= ~(UINT32_C(1) <<

Generated with cgit - Back to sebastiano.tronto.net