Update generator to favor collisions

This commit is contained in:
Minecon724 2024-10-07 16:58:08 +02:00
parent 6aab6e4b96
commit 45a9ae4f20
Signed by: Minecon724
GPG key ID: 3CCC4D267742C8E8

View file

@ -137,26 +137,79 @@ public class Generator {
} }
private Set<PlacedWord> follow(Grid grid, Set<PlacedWord> placedChain, int wordIndex) { private Set<PlacedWord> follow(Grid grid, Set<PlacedWord> placedChain, int wordIndex) {
//System.out.println("Depth " + wordIndex); System.out.println("Depth " + wordIndex);
if (wordIndex > peakDepth) if (wordIndex > peakDepth)
peakDepth = wordIndex; peakDepth = wordIndex;
if (wordIndex == words.length) { if (wordIndex == words.length) {
//System.out.println(" Completed"); System.out.println(" Completed");
return placedChain; return placedChain;
} }
List<Vec> currentPossiblePlacements = new ArrayList<>(possiblePlacements); List<Vec> currentPossiblePlacements = new ArrayList<>(possiblePlacements);
shuffle(currentPossiblePlacements); shuffle(currentPossiblePlacements);
//Collections.shuffle(currentPossiblePlacements);
boolean vertical = random.nextBoolean(); boolean vertical = random.nextBoolean();
Word word = words[wordIndex]; Word word = words[wordIndex];
// TODO optimize. maybe make this a list. and consider if this is really necessary.
Map<Integer, List<PlacedWord>> rankedPlacements = new LinkedHashMap<>();
int hi = -1;
for (int i=0; i<2; i++) { // repeating twice to pass horizontal and vertical for (int i=0; i<2; i++) { // repeating twice to pass horizontal and vertical
vertical = !vertical; vertical = !vertical;
for (Vec placement : currentPossiblePlacements) {
if (vertical) {
int y = placement.y();
if (y == 0 || y + word.length() >= height) continue;
} else {
int x = placement.x();
if (x == 0 || x + word.length() >= width) continue;
}
PlacedWord candidate = new PlacedWord(placement, vertical, word);
int placementResult = grid.canPlace(candidate);
if (placementResult != -1) {
//System.out.println(" Found candidate");
rankedPlacements.computeIfAbsent(placementResult, k -> new ArrayList<>()).add(candidate);
if (placementResult > hi) hi = placementResult;
}
}
}
System.out.println("hi " + hi);
for (int i=hi; i>=0; i--) {
//List<PlacedWord> candidates = rankedPlacements.getOrDefault(i, new ArrayList<>());
//System.out.println(" Candidates: " + candidates.size());
for (PlacedWord candidate : rankedPlacements.getOrDefault(i, new ArrayList<>())) {
Set<PlacedWord> potentialChain = new HashSet<>(placedChain);
potentialChain.add(candidate);
Grid newGrid = grid.clone();
newGrid.placeWord(candidate);
Set<PlacedWord> newChain = follow(newGrid, potentialChain, wordIndex + 1);
System.out.println("Back to depth " + wordIndex);
// if it's null it means there's no good placement, and we should continue searching at this depth
if (newChain != null) {
System.out.println(" Done here");
return newChain;
} else {
System.out.println(" Looking further");
}
}
}
/*for (int i=0; i<2; i++) { // repeating twice to pass horizontal and vertical
vertical = !vertical;
for (Vec placement : currentPossiblePlacements) { for (Vec placement : currentPossiblePlacements) {
if (vertical) { if (vertical) {
int y = placement.y(); int y = placement.y();
@ -188,9 +241,9 @@ public class Generator {
} }
} }
} }
} }*/
//System.out.println(" No solution"); System.out.println(" No solution");
// no placement at this depth // no placement at this depth
return null; return null;
} }