Skip to content
Snippets Groups Projects
Commit 2610bc51 authored by Christopher Bohn's avatar Christopher Bohn :thinking:
Browse files

Day 6 complete

parent 8e24234f
Branches
No related tags found
No related merge requests found
...@@ -36,3 +36,10 @@ O(num_lines * num_rows * num_columns); the algebraic approach would be ...@@ -36,3 +36,10 @@ O(num_lines * num_rows * num_columns); the algebraic approach would be
O(num_lines^2), so not too much of a big deal on this problem. But (I'm sure) O(num_lines^2), so not too much of a big deal on this problem. But (I'm sure)
there will be some problems whose straight-forward solution are a tad there will be some problems whose straight-forward solution are a tad
intractable. intractable.
## Day 6
For example, in the problem statement practically *screams* that the
obvious solution grows exponentially. Normally, death would keep the population
under control, but I guess Death Takes a Holiday. One little extra gotcha:
26984457539 > Integer.MAX_INT, so I need to use a long integer.
\ No newline at end of file
...@@ -11,8 +11,8 @@ public abstract class Puzzle { ...@@ -11,8 +11,8 @@ public abstract class Puzzle {
this.isProductionReady = isProductionReady; this.isProductionReady = isProductionReady;
} }
public abstract int computePart1(List<String> data); public abstract long computePart1(List<String> data);
public abstract int computePart2(List<String> data); public abstract long computePart2(List<String> data);
public void solvePuzzle(ImportData dataSource) { public void solvePuzzle(ImportData dataSource) {
List<String> data = null; List<String> data = null;
... ...
......
...@@ -37,13 +37,13 @@ public class Day1 extends Puzzle { ...@@ -37,13 +37,13 @@ public class Day1 extends Puzzle {
} }
@Override @Override
public int computePart1(List<String> data) { public long computePart1(List<String> data) {
depths = data.stream().map(Integer::parseInt).toList(); depths = data.stream().map(Integer::parseInt).toList();
return countIncreases(depths); return countIncreases(depths);
} }
@Override @Override
public int computePart2(List<String> data) { public long computePart2(List<String> data) {
int numberOfWindows = depths.size() - 2; int numberOfWindows = depths.size() - 2;
List<Integer> slidingWindows = new ArrayList<>(numberOfWindows); List<Integer> slidingWindows = new ArrayList<>(numberOfWindows);
for (int i = 0; i < numberOfWindows; i++) { for (int i = 0; i < numberOfWindows; i++) {
... ...
......
...@@ -11,10 +11,10 @@ public class Day2 extends Puzzle { ...@@ -11,10 +11,10 @@ public class Day2 extends Puzzle {
private List<NavigationInstruction> navigationInstructions; private List<NavigationInstruction> navigationInstructions;
private int range; private long range;
private int depth; private long depth;
@SuppressWarnings("FieldCanBeLocal") @SuppressWarnings("FieldCanBeLocal")
private int aim; private long aim;
public Day2(boolean isProductionReady) { public Day2(boolean isProductionReady) {
super(isProductionReady); super(isProductionReady);
...@@ -28,7 +28,7 @@ public class Day2 extends Puzzle { ...@@ -28,7 +28,7 @@ public class Day2 extends Puzzle {
} }
@Override @Override
public int computePart1(List<String> data) { public long computePart1(List<String> data) {
navigationInstructions = data.stream() navigationInstructions = data.stream()
.map(instruction -> new NavigationInstruction( .map(instruction -> new NavigationInstruction(
instruction.split(" ")[0], instruction.split(" ")[0],
...@@ -48,7 +48,7 @@ public class Day2 extends Puzzle { ...@@ -48,7 +48,7 @@ public class Day2 extends Puzzle {
} }
@Override @Override
public int computePart2(List<String> data) { public long computePart2(List<String> data) {
range = 0; range = 0;
depth = 0; depth = 0;
aim = 0; aim = 0;
... ...
......
...@@ -8,7 +8,7 @@ import java.util.function.BiPredicate; ...@@ -8,7 +8,7 @@ import java.util.function.BiPredicate;
@SuppressWarnings("unused") @SuppressWarnings("unused")
public class Day3 extends Puzzle { public class Day3 extends Puzzle {
private List<Integer> diagnosticReports; private List<Long> diagnosticReports;
private int reportLength; private int reportLength;
private int[] ones, zeroes; private int[] ones, zeroes;
...@@ -30,8 +30,8 @@ public class Day3 extends Puzzle { ...@@ -30,8 +30,8 @@ public class Day3 extends Puzzle {
} }
@Override @Override
public int computePart1(List<String> data) { public long computePart1(List<String> data) {
diagnosticReports = data.stream().map(report -> Integer.parseInt(report, 2)).toList(); diagnosticReports = data.stream().map(report -> Long.parseLong(report, 2)).toList();
reportLength = data.get(0).length(); reportLength = data.get(0).length();
ones = new int[]{ ones = new int[]{
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
...@@ -43,17 +43,17 @@ public class Day3 extends Puzzle { ...@@ -43,17 +43,17 @@ public class Day3 extends Puzzle {
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0}; 0, 0, 0, 0, 0, 0, 0, 0};
for (int report : diagnosticReports) { for (long report : diagnosticReports) {
for (int bit = 0; bit < reportLength; bit++) { for (int bit = 0; bit < reportLength; bit++) {
if ((report & (1 << bit)) == 0) { if ((report & 1L << bit) == 0) {
zeroes[bit]++; zeroes[bit]++;
} else { } else {
ones[bit]++; ones[bit]++;
} }
} }
} }
int gamma = 0; long gamma = 0;
int epsilon = 0; long epsilon = 0;
for (int bit = 0; bit < reportLength; bit++) { for (int bit = 0; bit < reportLength; bit++) {
if (ones[bit] > zeroes[bit]) { if (ones[bit] > zeroes[bit]) {
gamma |= (1 << bit); gamma |= (1 << bit);
...@@ -64,8 +64,8 @@ public class Day3 extends Puzzle { ...@@ -64,8 +64,8 @@ public class Day3 extends Puzzle {
return gamma * epsilon; return gamma * epsilon;
} }
private Integer filterReports(int[] onesArray, int[] zeroesArray, BiPredicate<Integer, Integer> predicate) { private Long filterReports(int[] onesArray, int[] zeroesArray, BiPredicate<Integer, Integer> predicate) {
List<Integer> workingSet = new ArrayList<>(diagnosticReports); List<Long> workingSet = new ArrayList<>(diagnosticReports);
int bit = reportLength - 1; int bit = reportLength - 1;
int numberOfOnes = onesArray[bit]; int numberOfOnes = onesArray[bit];
int numberOfZeroes = zeroesArray[bit]; int numberOfZeroes = zeroesArray[bit];
...@@ -84,8 +84,8 @@ public class Day3 extends Puzzle { ...@@ -84,8 +84,8 @@ public class Day3 extends Puzzle {
// Need to re-count the ones and zeroes since the old counts are now wrong // Need to re-count the ones and zeroes since the old counts are now wrong
if (bit >= 0) { if (bit >= 0) {
numberOfOnes = numberOfZeroes = 0; numberOfOnes = numberOfZeroes = 0;
for (int report : workingSet) { for (long report : workingSet) {
if ((report & (1 << bit)) == 0) { if ((report & (1L << bit)) == 0) {
numberOfZeroes++; numberOfZeroes++;
} else { } else {
numberOfOnes++; numberOfOnes++;
...@@ -97,10 +97,10 @@ public class Day3 extends Puzzle { ...@@ -97,10 +97,10 @@ public class Day3 extends Puzzle {
} }
@Override @Override
public int computePart2(List<String> data) { public long computePart2(List<String> data) {
Integer oxygenGeneratorRating = filterReports(ones, zeroes, Long oxygenGeneratorRating = filterReports(ones, zeroes,
(numberOfOnes, numberOfZeroes) -> numberOfOnes >= numberOfZeroes); (numberOfOnes, numberOfZeroes) -> numberOfOnes >= numberOfZeroes);
Integer co2ScrubberRating = filterReports(ones, zeroes, Long co2ScrubberRating = filterReports(ones, zeroes,
(numberOfOnes, numberOfZeroes) -> numberOfOnes < numberOfZeroes); (numberOfOnes, numberOfZeroes) -> numberOfOnes < numberOfZeroes);
return oxygenGeneratorRating * co2ScrubberRating; return oxygenGeneratorRating * co2ScrubberRating;
} }
... ...
......
...@@ -71,7 +71,7 @@ public class Day4 extends Puzzle { ...@@ -71,7 +71,7 @@ public class Day4 extends Puzzle {
} }
@Override @Override
public int computePart1(List<String> data) { public long computePart1(List<String> data) {
parseData(data); parseData(data);
Iterator<Integer> numberIterator = numbers.iterator(); Iterator<Integer> numberIterator = numbers.iterator();
while (cards.stream().noneMatch(BingoCard::hasBingo) && numberIterator.hasNext()) { while (cards.stream().noneMatch(BingoCard::hasBingo) && numberIterator.hasNext()) {
...@@ -85,7 +85,7 @@ public class Day4 extends Puzzle { ...@@ -85,7 +85,7 @@ public class Day4 extends Puzzle {
} }
@Override @Override
public int computePart2(List<String> data) { public long computePart2(List<String> data) {
Iterator<Integer> numberIterator = numbers.iterator(); Iterator<Integer> numberIterator = numbers.iterator();
while ((cards.stream().filter(BingoCard::hasBingo).count() < cards.size() - 1) && numberIterator.hasNext()) { while ((cards.stream().filter(BingoCard::hasBingo).count() < cards.size() - 1) && numberIterator.hasNext()) {
int number = numberIterator.next(); int number = numberIterator.next();
... ...
......
...@@ -95,13 +95,13 @@ public class Day5 extends Puzzle { ...@@ -95,13 +95,13 @@ public class Day5 extends Puzzle {
} }
@Override @Override
public int computePart1(List<String> data) { public long computePart1(List<String> data) {
parseData(data, false); parseData(data, false);
return countIntersectingVentLines(); return countIntersectingVentLines();
} }
@Override @Override
public int computePart2(List<String> data) { public long computePart2(List<String> data) {
parseData(data, true); parseData(data, true);
return countIntersectingVentLines(); return countIntersectingVentLines();
} }
... ...
......
package edu.unl.cse.bohn.year2021;
import edu.unl.cse.bohn.Puzzle;
import java.util.Arrays;
import java.util.List;
@SuppressWarnings("unused")
public class Day6 extends Puzzle {
private long[] numberOfFishAtCounter;
public Day6(boolean isProductionReady) {
super(isProductionReady);
sampleData = "3,4,3,1,2";
}
private void initializeFishCounters(List<String> data) {
List<Integer> fishCounters = Arrays.stream(data.get(0).split(","))
.mapToInt(Integer::parseInt)
.boxed().toList();
numberOfFishAtCounter = new long[9];
Arrays.fill(numberOfFishAtCounter, 0);
for (int fish : fishCounters) {
numberOfFishAtCounter[fish]++;
}
}
private void spawnFish(int numberOfDays) {
for (int day = 0; day < numberOfDays; day++) {
long spawningFish = numberOfFishAtCounter[0];
//noinspection ManualArrayCopy
for(int counter = 0; counter < 8; counter++) {
numberOfFishAtCounter[counter] = numberOfFishAtCounter[counter+1];
}
numberOfFishAtCounter[8] = spawningFish; // new fish
numberOfFishAtCounter[6] += spawningFish; // reset fish
}
}
@Override
public long computePart1(List<String> data) {
initializeFishCounters(data);
spawnFish(80);
return Arrays.stream(numberOfFishAtCounter).reduce(Long::sum).orElseThrow();
}
@Override
public long computePart2(List<String> data) {
initializeFishCounters(data);
spawnFish(256);
return Arrays.stream(numberOfFishAtCounter).reduce(Long::sum).orElseThrow();
}
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment