package main import ( "fmt" h "git.bullercodeworks.com/brian/adventofcode/helpers" ) func main() { inp := h.StdinToIntSlice() part1(inp) fmt.Println() part2(inp) } func part1(inp []int) { var total int for i := range inp { total += steps(inp[i], 2000) } fmt.Println("# Part 1") fmt.Println(total) } var cache map[int]map[string]int func part2(inp []int) { fmt.Println("# Part 2") cache = make(map[int]map[string]int) for i := range inp { wrk := inp[i] cache[inp[i]] = make(map[string]int) s := Seq{} for n := 0; n < 2000; n++ { next := step(wrk) seqChg := (next % 10) - (wrk % 10) s.Add(seqChg) if s.Len() == 4 { if _, ok := cache[inp[i]][s.String()]; !ok { cache[inp[i]][s.String()] = worth(next) } } wrk = next } } var best int var bestKey string checkedKeys := make(map[string]bool) for i := range inp { if i > 0 { h.ClearProgress() } h.PrintProgress(i, len(inp)) for k := range cache[inp[i]] { if _, ok := checkedKeys[k]; ok { continue } var total int for j := range inp { total += cache[inp[j]][k] } if total > best { best = total bestKey = k } checkedKeys[k] = true } } fmt.Println() fmt.Println("Most Bananas:", best, bestKey) } const prune = 16777216 func steps(n, cnt int) int { for i := 0; i < cnt; i++ { n = step(n) } return n } func step(n int) int { n ^= (n * 64) n %= prune n ^= (n / 32) n %= prune n ^= (n * 2048) n %= prune return n } func worth(n int) int { return n % 10 } type Seq struct { s []int } func (s *Seq) Len() int { return len(s.s) } func (s *Seq) Add(n int) { if len(s.s) >= 4 { s.s = append(s.s[1:], n) } else { s.s = append(s.s, n) } } func (s Seq) String() string { var ret string for i := range s.s { ret = fmt.Sprintf("%s,%d", ret, s.s[i]) } return ret[1:] }