h48

A prototype for an optimal Rubik's cube solver, work in progress.
git clone https://git.tronto.net/h48
Download | Log | Files | Refs | README | LICENSE

commit 7b1836b35e4e4e275c093f1a120db8006108b90d
parent 413cc53c97f5a665bf84098b47e8d2267002f3ce
Author: Sebastiano Tronto <sebastiano@tronto.net>
Date:   Mon, 20 May 2024 11:00:48 +0200

Added tests for h48 invcoord

Diffstat:
MTODO.txt | 2+-
Msrc/solve_h48.h | 30+++++++++++++++++-------------
Mtest/001_cube_conversion/cube_conversion_tests.c | 2--
Mtest/071_coord_eo/coord_eo_tests.c | 1-
Mtest/072_coord_co/coord_co_tests.c | 1-
Mtest/073_coord_csep/coord_csep_tests.c | 1-
Mtest/074_coord_esep/coord_esep_tests.c | 1-
Mtest/075_set_eo/set_eo_tests.c | 2--
Mtest/076_copy_corners/copy_corners_tests.c | 2--
Mtest/077_copy_edges/copy_edges_tests.c | 2--
Mtest/078_invcoord_esep/invcoord_esep_tests.c | 1-
Atest/101_coord_invcoord_h48/00_all.in | 8++++++++
Atest/101_coord_invcoord_h48/00_all.out | 8++++++++
Atest/101_coord_invcoord_h48/coord_invcoord_h48_tests.c | 40++++++++++++++++++++++++++++++++++++++++
Rtest/101_gendata_esep/00_all.in -> test/102_gendata_esep/00_all.in | 0
Rtest/101_gendata_esep/00_all.out -> test/102_gendata_esep/00_all.out | 0
Rtest/101_gendata_esep/gendata_esep_tests.c -> test/102_gendata_esep/gendata_esep_tests.c | 0
Mtest/test.h | 2++
18 files changed, 76 insertions(+), 27 deletions(-)

diff --git a/TODO.txt b/TODO.txt @@ -2,7 +2,7 @@ In progress: go back to nissy-style BFS for eosep data computation - (done) compute selfsim and cocsep representatives - (done) implement set_eo_fast for invcoord_h48 - (done) for invcoord_h48 remove erep, implement inverse esep coord - - add unit tests for invcoord_h48 (compute tables, if needed) + - (done) add unit tests for invcoord_h48 (compute tables, if needed) - change to BFS TODO pruning tables: diff --git a/src/solve_h48.h b/src/solve_h48.h @@ -8,13 +8,13 @@ #define ESEP_VISITEDSIZE ((ESEP_TABLESIZE * 2U + 7U) / 8U) #define ESEP_INFOSIZE 25 /* TODO unknown yet */ -#define H48_ESIZE ((_12c4 * _8c4) << h) +#define H48_ESIZE(h) ((_12c4 * _8c4) << (h)) -#define _esep_ind(i) (i / 8U) -#define _esep_shift(i) (4U * (i % 8U)) -#define _esep_mask(i) (((1U << 4U) - 1U) << _esep_shift(i)) -#define _visited_ind(i) (i / 8U) -#define _visited_mask(i) (1U << (i % 8U)) +#define _esep_ind(i) (i / 8U) +#define _esep_shift(i) (4U * (i % 8U)) +#define _esep_mask(i) (((1U << 4U) - 1U) << _esep_shift(i)) +#define _visited_ind(i) (i / 8U) +#define _visited_mask(i) (1U << (i % 8U)) typedef struct { cube_fast_t cube; @@ -70,22 +70,26 @@ coord_h48(cube_fast_t c, const uint32_t *cocsepdata, uint8_t h) esep = coord_fast_esep(d); eo = coord_fast_eo(d); - ret = (coclass * H48_ESIZE) + (esep << h) + (eo >> (11-h)); + ret = (coclass * H48_ESIZE(h)) + (esep << h) + (eo >> (11-h)); return ret; } +/* + +This function does not necessarily return a cube whose coordinate is +the given value, because it works up to symmetry. This means that the +returned cube is a transformed cube of one that gives the correct value. +*/ _static_inline cube_fast_t -invcoord_h48(int64_t i, const cube_fast_t *crep, uint8_t h) -{ - cube_fast_t ret; - int64_t coclass, ee, esep, eo; +invcoord_h48(int64_t i, const cube_fast_t *crep, uint8_t h) { + cube_fast_t ret; int64_t coclass, ee, esep, eo; DBG_ASSERT(h <= 11, cubetofast(zero), "invcoord_h48: h must be between 0 and 11\n"); - coclass = i / H48_ESIZE; - ee = i % H48_ESIZE; + coclass = i / H48_ESIZE(h); + ee = i % H48_ESIZE(h); esep = ee >> h; eo = (ee & ((1<<h)-1)) << (11-h); diff --git a/test/001_cube_conversion/cube_conversion_tests.c b/test/001_cube_conversion/cube_conversion_tests.c @@ -1,7 +1,5 @@ #include "../test.h" -cube_fast_t cubetofast(cube_t); -cube_t fasttocube(cube_fast_t); bool equal(cube_t, cube_t); int main(void) { diff --git a/test/071_coord_eo/coord_eo_tests.c b/test/071_coord_eo/coord_eo_tests.c @@ -1,7 +1,6 @@ #include "../test.h" int64_t coord_fast_eo(cube_fast_t); -cube_fast_t cubetofast(cube_t); int main(void) { char str[STRLENMAX]; diff --git a/test/072_coord_co/coord_co_tests.c b/test/072_coord_co/coord_co_tests.c @@ -1,7 +1,6 @@ #include "../test.h" int64_t coord_fast_co(cube_fast_t); -cube_fast_t cubetofast(cube_t); int main(void) { char str[STRLENMAX]; diff --git a/test/073_coord_csep/coord_csep_tests.c b/test/073_coord_csep/coord_csep_tests.c @@ -1,7 +1,6 @@ #include "../test.h" int64_t coord_fast_csep(cube_fast_t); -cube_fast_t cubetofast(cube_t); int main(void) { char str[STRLENMAX]; diff --git a/test/074_coord_esep/coord_esep_tests.c b/test/074_coord_esep/coord_esep_tests.c @@ -1,7 +1,6 @@ #include "../test.h" int64_t coord_fast_esep(cube_fast_t); -cube_fast_t cubetofast(cube_t); int main(void) { char str[STRLENMAX]; diff --git a/test/075_set_eo/set_eo_tests.c b/test/075_set_eo/set_eo_tests.c @@ -2,8 +2,6 @@ int64_t coord_fast_eo(cube_fast_t); void set_eo_fast(cube_fast_t *, int64_t); -cube_fast_t cubetofast(cube_t); -cube_t fasttocube(cube_fast_t); int main(void) { char str[STRLENMAX]; diff --git a/test/076_copy_corners/copy_corners_tests.c b/test/076_copy_corners/copy_corners_tests.c @@ -1,8 +1,6 @@ #include "../test.h" void copy_corners_fast(cube_fast_t *, cube_fast_t); -cube_fast_t cubetofast(cube_t); -cube_t fasttocube(cube_fast_t); int main(void) { char str[STRLENMAX]; diff --git a/test/077_copy_edges/copy_edges_tests.c b/test/077_copy_edges/copy_edges_tests.c @@ -1,8 +1,6 @@ #include "../test.h" void copy_edges_fast(cube_fast_t *, cube_fast_t); -cube_fast_t cubetofast(cube_t); -cube_t fasttocube(cube_fast_t); int main(void) { char str[STRLENMAX]; diff --git a/test/078_invcoord_esep/invcoord_esep_tests.c b/test/078_invcoord_esep/invcoord_esep_tests.c @@ -2,7 +2,6 @@ int64_t coord_fast_esep(cube_fast_t); cube_fast_t invcoord_fast_esep(int64_t); -cube_fast_t cubetofast(cube_t); int main(void) { char str[STRLENMAX]; diff --git a/test/101_coord_invcoord_h48/00_all.in b/test/101_coord_invcoord_h48/00_all.in @@ -0,0 +1,8 @@ +UB0 DF0 DB0 UF0 UR0 UL0 DL0 DR0 FR0 FL0 BL0 BR0 UFR0 UBL0 DFL0 DBR0 UFL0 UBR0 DFR0 DBL0 +UF0 UB0 DB0 DF0 UR0 UL0 DL0 DR0 FR0 FL0 BL0 BR0 UFR0 UBL0 DFL0 DBR0 UFL0 UBR0 DFR0 DBL0 +UB0 UF0 DB0 DF0 UL0 UR0 DL0 DR0 FR0 FL0 BL0 BR0 UBL0 UFR0 DFL0 DBR0 UBR0 UFL0 DFR0 DBL0 +UL0 BL0 BR1 DL0 FR0 DF0 DB1 DR1 UB0 FL0 UF0 UR1 DFL0 UFR1 DBR1 UBR2 DBL2 DFR0 UFL1 UBL2 +UF0 UB0 DB0 DF0 FR0 UL0 DL0 BR0 DR0 FL0 BL0 UR0 DFR2 UBL0 DFL0 UBR2 UFL0 UFR1 DBR1 DBL0 +FL1 UB0 DB0 FR1 UR0 UL0 DL0 DR0 UF1 DF1 BL0 BR0 UFL1 UBL0 DFR1 DBR0 DFL2 UBR0 UFR2 DBL0 +FR0 BR0 BL0 FL0 UR0 UL0 DL0 DR0 DF0 UF0 UB0 DB0 UFR0 UBL0 DFL0 DBR0 UFL0 UBR0 DFR0 DBL0 +UR0 UL0 DL0 DR0 UB0 UF0 DF0 DB0 FR0 FL0 BL0 BR0 UFR0 UBL0 DFL0 DBR0 UFL0 UBR0 DFR0 DBL0 diff --git a/test/101_coord_invcoord_h48/00_all.out b/test/101_coord_invcoord_h48/00_all.out @@ -0,0 +1,8 @@ +1 ok +2 ok +3 ok +4 ok +5 ok +6 ok +7 ok +8 ok diff --git a/test/101_coord_invcoord_h48/coord_invcoord_h48_tests.c b/test/101_coord_invcoord_h48/coord_invcoord_h48_tests.c @@ -0,0 +1,40 @@ +#include "../test.h" + +#define COCSEP_CLASSES 3393U + +size_t gendata_cocsep(void *, uint64_t *, cube_fast_t *); +int64_t coord_h48(cube_fast_t, const uint32_t *, uint8_t); +cube_fast_t invcoord_h48(int64_t, const cube_fast_t *, uint8_t); +cube_fast_t transform(cube_fast_t, uint8_t); + +int main(void) { + char str[STRLENMAX]; + int i; + bool found; + uint8_t h, t; + uint32_t cocsepdata[300000]; + uint64_t selfsim[COCSEP_CLASSES]; + int64_t c, cc; + cube_t cube; + cube_fast_t fast, invc, rep[COCSEP_CLASSES]; + + gendata_cocsep(cocsepdata, selfsim, rep); + + i = 1; + h = 11; + while (fgets(str, STRLENMAX, stdin) != NULL) { + cube = readcube("H48", str); + fast = cubetofast(cube); + c = coord_h48(fast, cocsepdata, h); + invc = invcoord_h48(c, rep, h); + for (t = 0, found = false; t < 48; t++) { + fast = transform(invc, t); + cc = coord_h48(fast, cocsepdata, h); + found = found || cc == c; + } + printf("%d %s\n", i, found ? "ok" : "ERROR"); + i++; + } + + return 0; +} diff --git a/test/101_gendata_esep/00_all.in b/test/102_gendata_esep/00_all.in diff --git a/test/101_gendata_esep/00_all.out b/test/102_gendata_esep/00_all.out diff --git a/test/101_gendata_esep/gendata_esep_tests.c b/test/102_gendata_esep/gendata_esep_tests.c diff --git a/test/test.h b/test/test.h @@ -26,3 +26,5 @@ bool issolvable(cube_t); bool issolved(cube_t); cube_t readcube(char *, char *); void writecube(char *, cube_t, char *); +cube_t fasttocube(cube_fast_t); +cube_fast_t cubetofast(cube_t);