Skip to content
advent of code 2023

day 12

hot springs

approach

count_ways is a memoized recursion over (i, j, c, prv): the position in the row, which group comes next, how long the current run of # is, and the previous character. a # extends the current run (or closes it when it reaches the group size), a . is only allowed outside a run, and right after a finished group the next spring is forced to be .. a ? tries both options.

part 1 sums the counts over all rows. part 2 unfolds each row into five copies joined by ? and the group list into five copies, and the same memoized count handles it.

the trick

memoize on position, group index and current run length, so the unfolded rows stay cheap.

python
if s[i] == "." and c == 0:
    return ways(i + 1, j, 0, ".")
if s[i] == "." and c > 0:
    return 0

if c + 1 < conts[j]:
    res = ways(i + 1, j, c + 1, "#")
else:
    res = ways(i + 1, j + 1, 0, "#")

if c == 0:
    res += ways(i + 1, j, 0, ".")

return res