Roderic Day před 5 roky
rodič
revize
9812344b3c
1 změnil soubory, kde provedl 27 přidání a 24 odebrání
  1. +27
    -24
      y2019/intcode.py

+ 27
- 24
y2019/intcode.py Zobrazit soubor

import re import re




def parse(string):
ns = [int(n) for n in re.findall(r'-?\d+', string)]
memory = collections.defaultdict(int)
memory.update(enumerate(ns))
return memory
MODES = {
'0': lambda ns, x, relbase: ns[x],
'1': lambda ns, x, relbase: x,
'2': lambda ns, x, relbase: ns[x + relbase],
'0-special': lambda ns, x, relbase: x,
'2-special': lambda ns, x, relbase: x + relbase,
}




def get_parameters(ns, pos, modes, N, writes, relbase): def get_parameters(ns, pos, modes, N, writes, relbase):
# paradox: return immediate mode to use positionally outside # paradox: return immediate mode to use positionally outside
modes[ord(c) - ord('a')] += '-special' modes[ord(c) - ord('a')] += '-special'


for mode, x in zip(modes, [ns[y] for y in range(pos, pos + N)]):
yield {
'0': lambda: ns[x],
'1': lambda: x,
'2': lambda: ns[x + relbase],
'0-special': lambda: x,
'2-special': lambda: x + relbase,
}[mode]()

yield pos + N yield pos + N
for i in range(N):
mode, x = modes[i], ns[pos + i]
yield MODES[mode](ns, x, relbase)




def compute(ns, in_iter): def compute(ns, in_iter):
op = ns[pos] % 100 op = ns[pos] % 100
# instructions stupidly say ABC referring to parameters 3, 2, 1 # instructions stupidly say ABC referring to parameters 3, 2, 1
# we do a, b, c # we do a, b, c
modes = list(str(ns[pos] // 100).zfill(3)[::-1])
modes = list(str(ns[pos] // 100)[::-1] + '000')
pos += 1 pos += 1


if op == 1: if op == 1:
a, b, c, pos = consume(3, 'c')
pos, a, b, c = consume(3, 'c')
ns[c] = a + b ns[c] = a + b


elif op == 2: elif op == 2:
a, b, c, pos = consume(3, 'c')
pos, a, b, c = consume(3, 'c')
ns[c] = a * b ns[c] = a * b


elif op == 3: elif op == 3:
a, pos = consume(1, 'a')
pos, a = consume(1, 'a')
ns[a] = next(in_iter) ns[a] = next(in_iter)


elif op == 4: elif op == 4:
a, pos = consume(1)
pos, a = consume(1)
yield a yield a


elif op == 5: elif op == 5:
a, b, pos = consume(2)
pos, a, b = consume(2)
if a != 0: if a != 0:
pos = b pos = b


elif op == 6: elif op == 6:
a, b, pos = consume(2)
pos, a, b = consume(2)
if a == 0: if a == 0:
pos = b pos = b


elif op == 7: elif op == 7:
a, b, c, pos = consume(3, 'c')
pos, a, b, c = consume(3, 'c')
ns[c] = int(a < b) ns[c] = int(a < b)


elif op == 8: elif op == 8:
a, b, c, pos = consume(3, 'c')
pos, a, b, c = consume(3, 'c')
ns[c] = int(a == b) ns[c] = int(a == b)


elif op == 9: elif op == 9:
a, pos = consume(1)
pos, a = consume(1)
relbase += a relbase += a


elif op == 99: elif op == 99:


else: else:
raise RuntimeError(op) raise RuntimeError(op)


def parse(string):
ns = [int(n) for n in re.findall(r'-?\d+', string)]
memory = collections.defaultdict(int)
memory.update(enumerate(ns))
return memory

Načítá se…
Zrušit
Uložit