Add Day10 implementation with puzzle-solving logic and tests
This commit is contained in:
parent
82772fd4e0
commit
6621a36021
|
|
@ -4,7 +4,7 @@ using System.Globalization;
|
||||||
using AoC_2025;
|
using AoC_2025;
|
||||||
|
|
||||||
var rootPath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
|
var rootPath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
|
||||||
var day01 = new Day01();
|
/*var day01 = new Day01();
|
||||||
string day01Path = @$"{rootPath}\AoC-PuzzleInputs\2025\Prod\day01.txt";
|
string day01Path = @$"{rootPath}\AoC-PuzzleInputs\2025\Prod\day01.txt";
|
||||||
Console.WriteLine(day01.SolvePart1(day01Path));
|
Console.WriteLine(day01.SolvePart1(day01Path));
|
||||||
Console.WriteLine(day01.SolvePart2(day01Path));
|
Console.WriteLine(day01.SolvePart2(day01Path));
|
||||||
|
|
@ -56,4 +56,10 @@ var day09 = new Day09();
|
||||||
string day09Path = @$"{rootPath}\AoC-PuzzleInputs\2025\Prod\day09.txt";
|
string day09Path = @$"{rootPath}\AoC-PuzzleInputs\2025\Prod\day09.txt";
|
||||||
Console.WriteLine(day09.SolvePart1(day09Path));
|
Console.WriteLine(day09.SolvePart1(day09Path));
|
||||||
Console.WriteLine(day09.SolvePart2(day09Path));
|
Console.WriteLine(day09.SolvePart2(day09Path));
|
||||||
|
Console.WriteLine();*/
|
||||||
|
|
||||||
|
var day10 = new Day10();
|
||||||
|
string day10Path = @$"{rootPath}\AoC-PuzzleInputs\2025\Prod\day10.txt";
|
||||||
|
Console.WriteLine(day10.SolvePart1(day10Path));
|
||||||
|
Console.WriteLine(day10.SolvePart2(day10Path));
|
||||||
Console.WriteLine();
|
Console.WriteLine();
|
||||||
|
|
@ -0,0 +1,47 @@
|
||||||
|
using AdvenOfCode.Contracts;
|
||||||
|
|
||||||
|
namespace AoC_2025.Tests;
|
||||||
|
|
||||||
|
public class Day10Test
|
||||||
|
{
|
||||||
|
private IPuzzleSolver<long> _sut;
|
||||||
|
private static readonly string rootPath = Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments);
|
||||||
|
private readonly string TestInputPath = @$"{rootPath}\AoC-PuzzleInputs\2025\Test\day10.txt";
|
||||||
|
private readonly string ProdInputPath = @$"{rootPath}\AoC-PuzzleInputs\2025\Prod\day10.txt";
|
||||||
|
|
||||||
|
public Day10Test()
|
||||||
|
{
|
||||||
|
_sut = new Day10();
|
||||||
|
}
|
||||||
|
[Fact]
|
||||||
|
public void Part01_Test_equals_7()
|
||||||
|
{
|
||||||
|
var actual = _sut.SolvePart1(TestInputPath);
|
||||||
|
|
||||||
|
Assert.Equal(7, actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void Part01_Prod_equals_500()
|
||||||
|
{
|
||||||
|
var actual = _sut.SolvePart1(ProdInputPath);
|
||||||
|
|
||||||
|
Assert.Equal(500, actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void Part02_Test_equals_24()
|
||||||
|
{
|
||||||
|
var actual = _sut.SolvePart2(TestInputPath);
|
||||||
|
|
||||||
|
Assert.Equal(24, actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void Part02_Prod_equals_1568849600()
|
||||||
|
{
|
||||||
|
var actual = _sut.SolvePart2(ProdInputPath);
|
||||||
|
|
||||||
|
Assert.Equal(1568849600, actual);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,96 @@
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Data;
|
||||||
|
using System.Data.Common;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using AdvenOfCode.Contracts;
|
||||||
|
|
||||||
|
namespace AoC_2025;
|
||||||
|
|
||||||
|
public class Day10 : IPuzzleSolver<long>
|
||||||
|
{
|
||||||
|
private static int done = 0;
|
||||||
|
private (uint lamps, uint[] buttons, int[] joltages)[] ParsePuzzleInput(string path)
|
||||||
|
{
|
||||||
|
var puzzleInput = File.ReadAllLines(path)
|
||||||
|
.Where(line => !string.IsNullOrWhiteSpace(line))
|
||||||
|
.Select(line => line.Split(' ', StringSplitOptions.RemoveEmptyEntries))
|
||||||
|
.Select(instruction => instruction switch
|
||||||
|
{
|
||||||
|
[var lamps, ..var buttons, var joltages] => (lamps: lamps[1..^1], buttons, joltages: joltages[1..^1]),
|
||||||
|
_ => throw new DataException("Misaligned data")
|
||||||
|
})
|
||||||
|
.OrderBy(inst => inst.lamps.Length)
|
||||||
|
.ToArray();
|
||||||
|
var lamps = puzzleInput
|
||||||
|
.Select(input => input.lamps)
|
||||||
|
.Select(lamps => lamps.Index())
|
||||||
|
.Select(ixlamps =>
|
||||||
|
ixlamps.Aggregate((uint)0L, (acc, ixLamp) => acc | ((uint)(ixLamp.Item == '#' ? 1L : 0L) << ixLamp.Index)))
|
||||||
|
.ToArray();
|
||||||
|
var buttons = puzzleInput
|
||||||
|
.Select(input => input.buttons)
|
||||||
|
.Select(buttons => buttons
|
||||||
|
.Select(button => button[1..^1]
|
||||||
|
.Split(',', StringSplitOptions.RemoveEmptyEntries)
|
||||||
|
.Select(lampIndex => int.Parse(lampIndex))
|
||||||
|
.Aggregate((uint)0L, (acc, lampIndex) => acc | ((uint)1 << lampIndex)))
|
||||||
|
.ToArray())
|
||||||
|
.ToArray();
|
||||||
|
var joltages = puzzleInput
|
||||||
|
.Select(input => input.joltages)
|
||||||
|
.Select(joltage => joltage
|
||||||
|
.Split(',', StringSplitOptions.RemoveEmptyEntries)
|
||||||
|
.Select(jolt => int.Parse(jolt))
|
||||||
|
.ToArray())
|
||||||
|
.ToArray();
|
||||||
|
var res = lamps
|
||||||
|
.Zip(buttons, (lamp, button) => (lamp, button))
|
||||||
|
.Zip(joltages, (bl, joltage) => (bl.lamp, bl.button, joltage))
|
||||||
|
.ToArray();
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
public long SolvePart1(string pathToPuzzleInput)
|
||||||
|
{
|
||||||
|
var instructions = ParsePuzzleInput(pathToPuzzleInput);
|
||||||
|
Console.WriteLine($"total: {instructions.Length}");
|
||||||
|
var minCounts = instructions
|
||||||
|
.Select(ins => GetMinCountButtonPressesForLamps(ins.lamps, ins.buttons))
|
||||||
|
.ToArray();
|
||||||
|
return minCounts.Sum();
|
||||||
|
}
|
||||||
|
|
||||||
|
public long SolvePart2(string pathToPuzzleInput)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static long GetMinCountButtonPressesForLamps(uint lamps, uint[] buttons)
|
||||||
|
{
|
||||||
|
var presses = 0L;
|
||||||
|
HashSet<uint> lampStates = [lamps];
|
||||||
|
while (lampStates.All(state => state > 0) && presses < 100)
|
||||||
|
{
|
||||||
|
lampStates = lampStates
|
||||||
|
.Select(lampState => GetLampStates(lampState, buttons))
|
||||||
|
.Aggregate((current, states) => [..current,..states])
|
||||||
|
.ToHashSet();
|
||||||
|
presses++;
|
||||||
|
}
|
||||||
|
|
||||||
|
var amount = Interlocked.Increment(ref done);
|
||||||
|
Console.WriteLine($"done: {amount}, presses: {presses}");
|
||||||
|
|
||||||
|
return presses;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static uint[] GetLampStates(uint lampState, uint[] buttons)
|
||||||
|
{
|
||||||
|
var states = buttons
|
||||||
|
.Where(button => (lampState & button) > 0)
|
||||||
|
.Select(button => lampState ^ button);
|
||||||
|
return [..states];
|
||||||
|
}
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue