# nix eval -f ./day_2_perf.nix part2 # nix eval -f ./day_2_perf.nix part2 --arg input 'builtins.readFile ./puzzle_cache/day_2_1' { input ? (builtins.readFile ./puzzle_cache/day_2_0), }: with builtins; with import ./utils.nix; let # part 2 any repeat num isStrPatternRepeated = str: let strLen = stringLength str; maxSplit = strLen / 2; # Only check up to half length since it must repeat at least twice splits = genList (i: i + 1) maxSplit; checkSplit = split: if mod strLen split == 0 then let count = strLen / split; firstElem = substring 0 split str; checkElem = index: if index >= count then true else if substring (index * split) split str == firstElem then checkElem (index + 1) else false; allPartsEqual = checkElem 1; in allPartsEqual else false; in any checkSplit splits; ranges = map (range: map (v: toIntBase10 v) (split "-" range)) (split "," input); sumBadIdsInRange = range: let from = elemAt range 0; to = elemAt range 1; ids = genList (i: from + i) (to - from + 1); processId = acc: id: let strId = toString id; in if isStrPatternRepeated strId then acc + id else acc; in (foldl' processId 0 ids); sumAllBadIds = sum (map sumBadIdsInRange ranges); in { part2 = sumAllBadIds; }