#define Day12 #if Day12 using System.Collections.Immutable; using AoC2021; const string START = "start"; const string END = "end"; var paths = new Dictionary>(); File.ReadAllLines("day12/input") .Select(l => l.Split("-")) .ForEachAsList(x => { if (x[0] != END && x[1] != START) { if (paths.ContainsKey(x[0])) { paths[x[0]] = paths[x[0]].Add(x[1]); } else { paths.Add(x[0], ImmutableHashSet.Create(x[1])); } } if (x[1] != END && x[0] != START) { if (paths.ContainsKey(x[1])) { paths[x[1]] = paths[x[1]].Add(x[0]); } else { paths.Add(x[1], ImmutableHashSet.Create(x[0])); } } }); Console.WriteLine(PathCountPart1(paths, ImmutableHashSet.Create(START), START)); Console.WriteLine(PathCountPart2(paths, ImmutableHashSet.Create(START), START, false)); long PathCountPart1(Dictionary> paths, ImmutableHashSet visitedSmallCaves, string current) { long count = paths[current].Contains(END) ? 1 : 0; ImmutableHashSet adjacent; adjacent = paths[current].Except(visitedSmallCaves).Remove(END); foreach (var a in adjacent) { if (a.ToLower() == a) { count += PathCountPart1(paths, visitedSmallCaves.Add(a), a); } else { count += PathCountPart1(paths, visitedSmallCaves, a); } } return count; } long PathCountPart2(Dictionary> paths, ImmutableHashSet visitedSmallCaves, string current, bool twice) { long count = paths[current].Contains(END) ? 1 : 0; ImmutableHashSet adjacent; if (twice) { adjacent = paths[current].Except(visitedSmallCaves).Remove(END); } else { adjacent = paths[current].Remove(END); } foreach (var a in adjacent) { if (a.ToLower() == a) { count += PathCountPart2(paths, visitedSmallCaves.Add(a), a, twice || visitedSmallCaves.Contains(a)); } else { count += PathCountPart2(paths, visitedSmallCaves, a, twice); } } return count; } #endif