You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
69 lines
1.7 KiB
69 lines
1.7 KiB
5 years ago
|
function check_mem(max, offs)
|
||
|
if max < offs then
|
||
|
print(string.format("Error: Memory offset out of bounds: %d", offs))
|
||
|
os.exit(false)
|
||
|
end
|
||
|
end
|
||
|
|
||
|
function interpret(mem)
|
||
|
pos = 1
|
||
|
while true do
|
||
|
if #mem < pos then
|
||
|
print(string.format("Instruction pointer ran off of memory"))
|
||
|
os.exit(false)
|
||
|
end
|
||
|
|
||
|
if mem[pos] == 1 or mem[pos] == 2 then
|
||
|
if #mem < pos + 3 then
|
||
|
print(string.format("Error: Opcode too short at end of memory: %d", pos))
|
||
|
os.exit(false)
|
||
|
end
|
||
|
arg1 = mem[pos + 1] + 1
|
||
|
arg2 = mem[pos + 2] + 1
|
||
|
res = mem[pos + 3] + 1
|
||
|
check_mem(#mem, arg1)
|
||
|
check_mem(#mem, arg2)
|
||
|
check_mem(#mem, res)
|
||
|
if mem[pos] == 1 then
|
||
|
mem[res] = mem[arg1] + mem[arg2]
|
||
|
else
|
||
|
mem[res] = mem[arg1] * mem[arg2]
|
||
|
end
|
||
|
|
||
|
pos = pos + 4
|
||
|
elseif mem[pos] == 99 then
|
||
|
return
|
||
|
else
|
||
|
print(string.format("Error: Invalid opcode %d at %d", mem[pos], pos - 1))
|
||
|
os.exit(false)
|
||
|
end
|
||
|
end
|
||
|
end
|
||
|
|
||
|
file = io.open(arg[1])
|
||
|
memory = {}
|
||
|
for num in string.gmatch(file:read(), "(%d+),") do
|
||
|
table.insert(memory, tonumber(num))
|
||
|
end
|
||
|
file:close()
|
||
|
|
||
|
memory_p1 = {table.unpack(memory)}
|
||
|
memory_p1[2] = 12
|
||
|
memory_p1[3] = 2
|
||
|
interpret(memory_p1)
|
||
|
print("Part 1:", memory_p1[1])
|
||
|
|
||
|
-- Brute force
|
||
|
for noun = 0, 99 do
|
||
|
for verb = 0, 99 do
|
||
|
memory_p2 = {table.unpack(memory)}
|
||
|
memory_p2[2] = noun
|
||
|
memory_p2[3] = verb
|
||
|
interpret(memory_p2)
|
||
|
if memory_p2[1] == 19690720 then
|
||
|
print("Part 2:", 100 * noun + verb)
|
||
|
os.exit(true)
|
||
|
end
|
||
|
end
|
||
|
end
|