package days import ( "fmt" u "parnic.com/aoc2019/utilities" ) type Day19 struct { program u.IntcodeProgram } func (d *Day19) Parse() { d.program = u.LoadIntcodeProgram("19p") } func (d Day19) Num() int { return 19 } func (d *Day19) Part1() string { grid := make([][]bool, 50) for y := 0; y < len(grid); y++ { grid[y] = make([]bool, 50) } count := int64(0) for y := 0; y < 50; y++ { for x := 0; x < 50; x++ { d.program.Reset() d.program.RunIn(func(inputStep int) int64 { if inputStep == 1 { return int64(x) } return int64(y) }, func(val int64, state u.IntcodeProgramState) { res := val == 1 grid[y][x] = res if res { count++ } }) } } // fmt.Println("50x50 tractor view:") // for y := 0; y < len(grid); y++ { // for x := 0; x < len(grid[y]); x++ { // if grid[y][x] { // fmt.Print("█") // } else { // fmt.Print(" ") // } // } // fmt.Println() // } return fmt.Sprintf("Points affected in 50x50 area: %s%d%s", u.TextBold, count, u.TextReset) } func (d *Day19) Part2() string { f := func(x, y int) bool { ret := false d.program.Reset() d.program.RunIn(func(inputStep int) int64 { if inputStep == 1 { return int64(x) } return int64(y) }, func(val int64, state u.IntcodeProgramState) { ret = val == 1 }) return ret } // find lower bound startY := 0 startX := 0 for y := 1; startY == 0; y++ { for x := 0; x < 10*y; x++ { if f(x, y) { startY = y startX = x break } } } lastGoodX := 0 threshold := 1 y := u.Bisect(startY+100, 9999, threshold, func(y int) bool { foundX := false for x := startX; ; x++ { if !f(x, y) { if !foundX { continue } else { return true } } if !foundX { foundX = true } if !f(x+99, y) { return true } if !f(x, y+99) { continue } lastGoodX = x return false } }) result := (lastGoodX * 10000) + y return fmt.Sprintf("Closest 100x100 square for the ship starts at %d,%d = %s%d%s", lastGoodX, y, u.TextBold, result, u.TextReset) }