diff options
Diffstat (limited to 'solutions/py/intcode.py')
| -rw-r--r-- | solutions/py/intcode.py | 62 |
1 files changed, 48 insertions, 14 deletions
diff --git a/solutions/py/intcode.py b/solutions/py/intcode.py index f83a7ef..0f17962 100644 --- a/solutions/py/intcode.py +++ b/solutions/py/intcode.py @@ -1,4 +1,4 @@ -params = {1:3, 2:3, 3:1, 4:1, 5:2, 6:2, 7:3, 8:3, 99:0} +param_amount = {1:3, 2:3, 3:1, 4:1, 5:2, 6:2, 7:3, 8:3, 9:1, 99:0} ADD = 1 MULT = 2 @@ -8,43 +8,74 @@ JNZ = 5 JEZ = 6 LET = 7 EQV = 8 +BAS = 9 HAL = 99 class Computer(object): def __init__(self, program): self.memory = program.copy() + self.memory_size = len(self.memory) # pointers greater than this go in extra memory self.pointer = 0 - self.phase_read = False + self.phase_read = False # for day 7 + self.relative_base = 0 + self.extra_mem = {} self.input = None self.output = None def parse_op(self, op): + #TODO code = op % 100 - return [code] + [(op // 10**(i+2)) % 10**(i+1) for i in range(params[code])] + ops = str(op).zfill(param_amount[code]+2) + return [code] + [int(x) for x in ops[:-2][::-1]] + #return [code] + [(op // 10**(i+2)) % 10**(i+1) for i in range(param_amount[code])] def clear_flags(self): self.input = None self.output = None + def write(self, addr, val): + if addr > self.memory_size: + self.extra_mem[addr] = val + else: + self.memory[addr] = val + + def get(self, addr): + if addr > self.memory_size: + return self.extra_mem[addr] if addr in self.extra_mem else 0 + else: + return self.memory[addr] + def get_param(self, inst, num): - return self.memory[self.pointer + num] if inst[num] == True else\ - self.memory[self.memory[self.pointer + num]] + if inst[num] == 0: + return self.get(self.get(self.pointer + num)) + elif inst[num] == 1: + return self.get(self.pointer + num) + elif inst[num] == 2: + return self.get(self.relative_base + self.get(self.pointer + num)) + + def write_param(self, inst, num, val): + if inst[num] == 0: + self.write(self.get(self.pointer + num), val) + elif inst[num] == 1: + self.write(self.pointer + num, val) + elif inst[num] == 2: + self.write(self.relative_base + self.get(self.pointer + num), val) def step(self): inst = self.parse_op(self.memory[self.pointer]) if inst[0] == HAL: return elif inst[0] == ADD: - self.memory[self.memory[self.pointer+3]] = \ - self.get_param(inst, 1) + self.get_param(inst, 2) + self.write_param(inst, 3, \ + self.get_param(inst, 1) + self.get_param(inst, 2)) self.pointer += 4 elif inst[0] == MULT: - self.memory[self.memory[self.pointer+3]] = \ - self.get_param(inst, 1) * self.get_param(inst, 2) + self.write_param(inst, 3, \ + self.get_param(inst, 1) * self.get_param(inst, 2)) self.pointer += 4 elif inst[0] == IN: - self.memory[self.memory[self.pointer+1]] = self.input + self.write_param(inst, 1, self.input) self.input = None self.pointer += 2 elif inst[0] == OUT: @@ -61,15 +92,18 @@ class Computer(object): else: self.pointer += 3 elif inst[0] == LET: - self.memory[self.memory[self.pointer+3]] = 1 if \ + self.write_param(inst, 3, 1 if \ self.get_param(inst, 1) < self.get_param(inst, 2) \ - else 0 + else 0) self.pointer += 4 elif inst[0] == EQV: - self.memory[self.memory[self.pointer+3]] = 1 if \ + self.write_param(inst, 3, 1 if \ self.get_param(inst, 1) == self.get_param(inst, 2) \ - else 0 + else 0) self.pointer += 4 + elif inst[0] == BAS: + self.relative_base += self.get_param(inst, 1) + self.pointer += 2 else: print(self.memory) print(self.pointer) |
