mirror of
https://github.com/onyx-and-iris/aoc2024.git
synced 2025-01-09 14:20:48 +00:00
51 lines
1.1 KiB
Go
51 lines
1.1 KiB
Go
package one
|
|
|
|
import (
|
|
"bytes"
|
|
"math"
|
|
"sort"
|
|
"strings"
|
|
)
|
|
|
|
func Solve(buf []byte) (int, error) {
|
|
r := bytes.NewReader(buf)
|
|
wires, expressions, err := parseLines(r)
|
|
if err != nil {
|
|
return 0, err
|
|
}
|
|
|
|
wires = calculateWire(expressions, wires)
|
|
zWires := filter(wires, func(name string) bool {
|
|
return strings.HasPrefix(name, "z")
|
|
})
|
|
sort.Sort(byName(zWires))
|
|
|
|
var decimal int
|
|
for i, zWire := range zWires {
|
|
decimal += zWire.value * int(math.Pow(float64(2), float64(i)))
|
|
}
|
|
|
|
return decimal, nil
|
|
}
|
|
|
|
func calculateWire(expressions []expression, wires map[string]int) map[string]int {
|
|
if !anyNegative(wires) {
|
|
return wires
|
|
}
|
|
|
|
for _, expression := range expressions {
|
|
if wires[expression.left] != noValue && wires[expression.right] != noValue {
|
|
switch expression.op {
|
|
case AND:
|
|
wires[expression.target] = wires[expression.left] & wires[expression.right]
|
|
case OR:
|
|
wires[expression.target] = wires[expression.left] | wires[expression.right]
|
|
case XOR:
|
|
wires[expression.target] = wires[expression.left] ^ wires[expression.right]
|
|
}
|
|
}
|
|
}
|
|
|
|
return calculateWire(expressions, wires)
|
|
}
|