diff --git a/2021/day24/main.go b/2021/day24/main.go index a63e1d3..0752c6e 100644 --- a/2021/day24/main.go +++ b/2021/day24/main.go @@ -1,220 +1,54 @@ package main import ( - "bufio" "fmt" - "math" - "os" - "strconv" "strings" h "git.bullercodeworks.com/brian/adventofcode/helpers" ) func main() { - fmt.Println("ALU") - if len(os.Args) < 2 { - fmt.Println("Must pass filename as argument") - os.Exit(1) - } - test(os.Args[1]) - //part1(os.Args[1]) + inp := h.StdinToStringSlice() + solve(1, inp) + fmt.Println("") + solve(2, inp) } -func test(fn string) { - fmt.Println("# Test") - num := "15" - alu := NewALU() - alu.ReadProgram(fn) - var done bool - for !done { - fmt.Println("Converting", num) - alu.BufferInput(strings.Split(num, "")) - alu.run() - if num == "0" { - done = true - } - num = decNum(num, len(num)-1) - } +type pair struct { + first int + second int } -func decNum(num string, idx int) string { - if idx < 0 { - return num - } - if len(num) < idx { - return num - } - if num[idx] == '0' && idx > 0 { - num = num[:idx] + "9" + num[idx+1:] - return decNum(num, idx-1) - } - num = num[:idx] + string(num[idx]-1) + num[idx+1:] - return num -} - -func part1(fn string) { - fmt.Println("# Part 1") - var done bool - num := "99999999999999" - alu := NewALU() - alu.ReadProgram(fn) - for !done { - fmt.Println("Checking Model No.", num) - alu.BufferInput(strings.Split(num, "")) - alu.run() - if alu.registers["z"] == 0 { - fmt.Println("-> It's good.") - done = true - } - num = decModelNum(num, len(num)-1) - } -} - -func decModelNum(num string, idx int) string { - if len(num) < idx { - return num - } - if num[idx] == '1' { - num = num[:idx] + "9" + num[idx+1:] - return decModelNum(num, idx-1) - } - num = num[:idx] + string(num[idx]-1) + num[idx+1:] - return num -} - -const ( - INPUT_MODE_USER = iota - INPUT_MODE_CHAN -) - -type ALU struct { - program []string - registers map[string]int - ptr int - inputMode int - inputChan chan string -} - -func NewALU() *ALU { - return &ALU{ - registers: map[string]int{"w": 0, "x": 0, "y": 0, "z": 0}, - ptr: 0, - inputChan: make(chan string, 14), - } -} - -func (alu *ALU) BufferInput(inp []string) { - alu.inputMode = INPUT_MODE_CHAN - for i := range inp { - alu.inputChan <- inp[i] - } -} - -func (alu *ALU) ReadProgram(fn string) error { - file, err := os.Open(fn) - if err != nil { - return err - } - defer file.Close() - - var lines []string - scanner := bufio.NewScanner(file) - for scanner.Scan() { - lines = append(lines, scanner.Text()) - } - alu.program = lines - return scanner.Err() -} - -func (alu *ALU) printRegisters() { - fmt.Printf("Registers:\nw: %d\nx: %d\ny: %d\nz: %d\n", alu.registers["w"], alu.registers["x"], alu.registers["y"], alu.registers["z"]) -} - -func (alu *ALU) run() { - for alu.ptr = 0; alu.ptr < len(alu.program); alu.ptr++ { - pts := strings.Split(alu.program[alu.ptr], " ") - switch pts[0] { - case "inp": - alu.registers[pts[1]] = alu.inp() - case "add": - alu.registers[pts[1]] = alu.add(alu.value(pts[1]), alu.value(pts[2])) - case "mul": - alu.registers[pts[1]] = alu.mul(alu.value(pts[1]), alu.value(pts[2])) - case "div": - alu.registers[pts[1]] = alu.div(alu.value(pts[1]), alu.value(pts[2])) - case "mod": - alu.registers[pts[1]] = alu.mod(alu.value(pts[1]), alu.value(pts[2])) - case "eql": - alu.registers[pts[1]] = alu.eql(alu.value(pts[1]), alu.value(pts[2])) - } - } -} - -func (alu *ALU) inp() int { - if alu.inputMode == INPUT_MODE_USER { - var inp string - var err error - var v int - for inp == "" || err != nil { - fmt.Println("Input value:") - reader := bufio.NewReader(os.Stdin) - inp, _ = reader.ReadString('\n') - inp = strings.TrimSpace(inp) - v, err = strconv.Atoi(inp) - if err != nil { - fmt.Println("Must be an integer.") +func solve(part int, inp []string) { + var model [14]int + var stack []pair + for i := 0; i < 14; i++ { + xAdd := h.Atoi(strings.Fields(inp[18*i+5])[2]) + yAdd := h.Atoi(strings.Fields(inp[18*i+15])[2]) + if xAdd > 0 { + stack = append(stack, pair{first: yAdd, second: i}) + } else { + var s pair + var toAdd int + s, stack = stack[len(stack)-1], stack[:len(stack)-1] + if part == 1 { + toAdd = 9 + for toAdd+s.first+xAdd > 9 { + toAdd-- + } + } else if part == 2 { + toAdd = 1 + for toAdd+s.first+xAdd < 1 { + toAdd++ + } } - } - return v - } else if alu.inputMode == INPUT_MODE_CHAN { - v, err := strconv.Atoi(<-alu.inputChan) - if err == nil { - return v + model[s.second] = toAdd + model[i] = toAdd + s.first + xAdd } } - return 0 -} - -func (alu *ALU) value(a string) int { - switch a { - case "w", "x", "y", "z": - return alu.registers[a] - default: - return h.Atoi(a) + fmt.Println("# Part", part) + for i := range model { + fmt.Print(model[i]) } -} - -func (alu *ALU) add(a, b int) int { - return a + b -} - -func (alu *ALU) mul(a, b int) int { - return a * b -} - -func (alu *ALU) div(a, b int) int { - if b == 0 { - return 0 - } - aD, bD := float64(a), float64(b) - d := aD / bD - if d > 0 { - return int(math.Floor(d)) - } - return int(math.Ceil(d)) -} - -func (alu *ALU) mod(a, b int) int { - if a < 0 || b <= 0 { - return 0 - } - return a % b -} - -func (alu *ALU) eql(a, b int) int { - if a == b { - return 1 - } - return 0 + fmt.Println() } diff --git a/2021/day24/parts.csv b/2021/day24/parts.csv new file mode 100644 index 0000000..88220e5 --- /dev/null +++ b/2021/day24/parts.csv @@ -0,0 +1,18 @@ +inp w,inp w,inp w,inp w,inp w,inp w,inp w,inp w,inp w,inp w,inp w,inp w,inp w,inp w +mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0,mul x 0 +add x z,add x z,add x z,add x z,add x z,add x z,add x z,add x z,add x z,add x z,add x z,add x z,add x z,add x z +mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26,mod x 26 +div z 1,div z 1,div z 1,div z 26,div z 1,div z 26,div z 1,div z 1,div z 1,div z 26,div z 26,div z 26,div z 26,div z 26 +add x 10,add x 13,add x 13,add x -11,add x 11,add x -4,add x 12,add x 12,add x 15,add x -2,add x -5,add x -11,add x -13,add x -10 +eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w,eql x w +eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0,eql x 0 +mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0 +add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25,add y 25 +mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x +add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1,add y 1 +mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y,mul z y +mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0,mul y 0 +add y w,add y w,add y w,add y w,add y w,add y w,add y w,add y w,add y w,add y w,add y w,add y w,add y w,add y w +add y 13,add y 10,add y 3,add y 1,add y 9,add y 3,add y 5,add y 1,add y 0,add y 13,add y 7,add y 15,add y 12,add y 8 +mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x,mul y x +add z y,add z y,add z y,add z y,add z y,add z y,add z y,add z y,add z y,add z y,add z y,add z y,add z y,add z y