Gather data
This commit is contained in:
@@ -28,7 +28,7 @@ import java.util.function.Supplier;
|
||||
* java SwedishGenerator [--seed N] [--pop N] [--gens N] [--tries N] [--words word-list.txt]
|
||||
*/
|
||||
@SuppressWarnings("ALL")
|
||||
public record SwedishGenerator() {
|
||||
public record SwedishGenerator(Rng rng) {
|
||||
|
||||
record CandidateInfo(int[] indices, int count) { }
|
||||
|
||||
@@ -36,11 +36,11 @@ public record SwedishGenerator() {
|
||||
@FunctionalInterface interface SlotVisitor { void visit(int key, long packedPos, int len); }
|
||||
//@formatter:on
|
||||
static final int BAR_LEN = 22;
|
||||
static final int C = Config.PUZZLE_COLS;
|
||||
static final double CROSS_Y = (C - 1) / 2.0;
|
||||
static final int R = Config.PUZZLE_ROWS;
|
||||
static final double CROSS_X = (R - 1) / 2.0;
|
||||
static final int SIZE = C * R;// ~18
|
||||
static final int C = Config.PUZZLE_COLS;
|
||||
static final double CROSS_R = (C - 1) / 2.0;
|
||||
static final int R = Config.PUZZLE_ROWS;
|
||||
static final double CROSS_C = (R - 1) / 2.0;
|
||||
static final int SIZE = C * R;// ~18
|
||||
static final double SIZED = (double) SIZE;// ~18
|
||||
static final int TARGET_CLUES = SIZE >> 2;
|
||||
static final int MAX_WORD_LENGTH = C <= R ? C : R;
|
||||
@@ -237,7 +237,7 @@ public record SwedishGenerator() {
|
||||
return same / SIZED;
|
||||
}
|
||||
int clueCount() { return Long.bitCount(bo[0]) + Long.bitCount(bo[1]); }
|
||||
void forEachSetBit71() { forEachSetBit71(null); }
|
||||
|
||||
void forEachSetBit71(IntConsumer consumer) {
|
||||
for (var lo = bo[0]; lo != 0; lo &= lo - 1) consumer.accept(Long.numberOfTrailingZeros(lo));
|
||||
for (var hi = bo[1]; hi != 0; hi &= hi - 1) consumer.accept(64 + Long.numberOfTrailingZeros(hi));
|
||||
@@ -285,7 +285,7 @@ public record SwedishGenerator() {
|
||||
|
||||
static final Gson GSON = new Gson();
|
||||
public Dict(Lemma[] wordz) {
|
||||
var index = new DictEntry[MAX_WORD_LENGTH_PLUS_ONE];
|
||||
var index = new DictEntry[MAX_WORD_LENGTH_PLUS_ONE];
|
||||
Arrays.setAll(index, i -> new DictEntry(i));
|
||||
for (var lemma : wordz) {
|
||||
var L = lemma.word.length;
|
||||
@@ -385,7 +385,7 @@ public record SwedishGenerator() {
|
||||
public static int offset(long packedPos, int i) { return (int) ((packedPos >> (i * 7)) & 127); }
|
||||
}
|
||||
|
||||
private static void processSlot(Grid grid, SwedishGenerator.SlotVisitor visitor, int idx) {
|
||||
private static void processSlot(Grid grid, SlotVisitor visitor, int idx) {
|
||||
var d = grid.digitAt(idx);
|
||||
var nbrs16 = OFFSETS[d];
|
||||
int r = Grid.r(idx), c = Grid.c(idx), rr = r + nbrs16.r, cc = c + nbrs16.c;
|
||||
@@ -544,7 +544,7 @@ public record SwedishGenerator() {
|
||||
return penalty[0];
|
||||
}
|
||||
|
||||
Grid randomMask(Rng rng) {
|
||||
Grid randomMask() {
|
||||
var g = Grid.createEmpty();
|
||||
int placed = 0, guard = 0;
|
||||
|
||||
@@ -561,7 +561,7 @@ public record SwedishGenerator() {
|
||||
}
|
||||
return g;
|
||||
}
|
||||
Grid mutate(Rng rng, Grid grid) {
|
||||
Grid mutate(Grid grid) {
|
||||
var g = grid.deepCopyGrid();
|
||||
var cx = rng.randint(0, R - 1);
|
||||
var cy = rng.randint(0, C - 1);
|
||||
@@ -581,24 +581,24 @@ public record SwedishGenerator() {
|
||||
}
|
||||
return g;
|
||||
}
|
||||
Grid crossover(Rng rng, Grid a, Grid b) {
|
||||
Grid crossover(Grid a, Grid b) {
|
||||
var out = Grid.createEmpty();
|
||||
var theta = rng.nextFloat() * Math.PI;
|
||||
var nx = Math.cos(theta);
|
||||
var ny = Math.sin(theta);
|
||||
var nc = Math.cos(theta);
|
||||
var nr = Math.sin(theta);
|
||||
|
||||
for (var rci : IT) out.setAt(rci.i, ((rci.r - CROSS_X) * nx + (rci.c - CROSS_Y) * ny >= 0) ? a.byteAt(rci.i) : b.byteAt(rci.i));
|
||||
for (var rci : IT) out.setAt(rci.i, ((rci.r - CROSS_C) * nc + (rci.c - CROSS_R) * nr >= 0) ? a.byteAt(rci.i) : b.byteAt(rci.i));
|
||||
for (var rci : IT) if (out.isDigitAt(rci.i) && !hasRoomForClue(out, rci.i, OFFSETS[out.digitAt(rci.i)])) out.clearClue(rci.i);
|
||||
return out;
|
||||
}
|
||||
|
||||
Grid hillclimb(Rng rng, Grid start, int limit) {
|
||||
Grid hillclimb(Grid start, int limit) {
|
||||
var best = start;
|
||||
var bestF = maskFitness(best);
|
||||
var fails = 0;
|
||||
|
||||
while (fails < limit) {
|
||||
var cand = mutate(rng, best);
|
||||
var cand = mutate(best);
|
||||
var f = maskFitness(cand);
|
||||
if (f < bestF) {
|
||||
best = cand;
|
||||
@@ -611,7 +611,7 @@ public record SwedishGenerator() {
|
||||
return best;
|
||||
}
|
||||
|
||||
public Grid generateMask(Rng rng, int popSize, int gens) {
|
||||
public Grid generateMask(int popSize, int gens) {
|
||||
class GridAndFit {
|
||||
|
||||
Grid grid;
|
||||
@@ -625,7 +625,7 @@ public record SwedishGenerator() {
|
||||
if (Main.VERBOSE) System.out.println("generateMask init pop: " + popSize);
|
||||
var pop = new ArrayList<GridAndFit>();
|
||||
for (var i = 0; i < popSize; i++) {
|
||||
pop.add(new GridAndFit(hillclimb(rng, randomMask(rng), 180)));
|
||||
pop.add(new GridAndFit(hillclimb(randomMask(), 180)));
|
||||
}
|
||||
|
||||
for (var gen = 0; gen < gens; gen++) {
|
||||
@@ -636,8 +636,8 @@ public record SwedishGenerator() {
|
||||
for (var k = 0; k < pairs; k++) {
|
||||
var p1 = pop.get(rng.randint(0, pop.size() - 1));
|
||||
var p2 = pop.get(rng.randint(0, pop.size() - 1));
|
||||
var child = crossover(rng, p1.grid, p2.grid);
|
||||
children.add(new GridAndFit(hillclimb(rng, child, 70)));
|
||||
var child = crossover(p1.grid, p2.grid);
|
||||
children.add(new GridAndFit(hillclimb(child, 70)));
|
||||
}
|
||||
|
||||
pop.addAll(children);
|
||||
@@ -797,7 +797,7 @@ public record SwedishGenerator() {
|
||||
var entry = dictIndex[s.len()];
|
||||
if (entry == null) return PICK_NOT_DONE;
|
||||
patternForSlot(grid, s, ctx.pattern);
|
||||
var info = SwedishGenerator.candidateInfoForPattern(ctx, entry, s.len());
|
||||
var info = candidateInfoForPattern(ctx, entry, s.len());
|
||||
|
||||
if (info.count == 0) return PICK_NOT_DONE;
|
||||
var slotScore = -1;
|
||||
|
||||
Reference in New Issue
Block a user