intcode programs running again, but horribly slow
This commit is contained in:
parent
b9c38b72bd
commit
e3b847bdf6
38
day01.py
38
day01.py
@ -1,6 +1,19 @@
|
||||
from tools.aoc import AOCDay
|
||||
|
||||
|
||||
def get_fuel(count: int, part2: bool = False):
|
||||
if not part2:
|
||||
return count // 3 - 2
|
||||
else:
|
||||
fuel_sum = 0
|
||||
count = count // 3 - 2
|
||||
while count > 0:
|
||||
fuel_sum += count
|
||||
count = count // 3 - 2
|
||||
|
||||
return fuel_sum
|
||||
|
||||
|
||||
class Day(AOCDay):
|
||||
inputs = [
|
||||
[
|
||||
@ -18,22 +31,21 @@ class Day(AOCDay):
|
||||
]
|
||||
]
|
||||
|
||||
def part1(self):
|
||||
fuel_sum = 0
|
||||
for x in self.getInputListAsType(int):
|
||||
fuel_sum += x // 3 - 2
|
||||
def get_fuel(self, part2: bool = False):
|
||||
if len(self.input) == 1:
|
||||
return get_fuel(self.getInput(int), part2)
|
||||
else:
|
||||
fuel_sum = 0
|
||||
for x in self.getInput(int):
|
||||
fuel_sum += get_fuel(x, part2)
|
||||
|
||||
return fuel_sum
|
||||
return fuel_sum
|
||||
|
||||
def part1(self):
|
||||
return self.get_fuel()
|
||||
|
||||
def part2(self):
|
||||
fuel_sum = 0
|
||||
for x in self.getInputListAsType(int):
|
||||
fuel_add = x // 3 - 2
|
||||
while fuel_add > 0:
|
||||
fuel_sum += fuel_add
|
||||
fuel_add = fuel_add // 3 - 2
|
||||
|
||||
return fuel_sum
|
||||
return self.get_fuel(True)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
6
day07.py
6
day07.py
@ -7,7 +7,7 @@ from typing import Any, List
|
||||
def get_comps(memory: List[int]) -> List[IntCode]:
|
||||
comps = []
|
||||
for _ in range(5):
|
||||
comps.append(IntCode(memory.copy()))
|
||||
comps.append(IntCode(memory))
|
||||
|
||||
return comps
|
||||
|
||||
@ -41,7 +41,7 @@ class Day(AOCDay):
|
||||
|
||||
comps[i].addInput(input1)
|
||||
comps[i].addInput(input2)
|
||||
comps[i].run()
|
||||
comps[i].start()
|
||||
|
||||
signal = comps[4].getOutput()
|
||||
if signal > max_signal:
|
||||
@ -54,7 +54,7 @@ class Day(AOCDay):
|
||||
max_signal = 0
|
||||
phase_settings = [5, 6, 7, 8, 9]
|
||||
for s in itertools.permutations(phase_settings):
|
||||
comps = get_comps(init_memory.copy())
|
||||
comps = get_comps(init_memory)
|
||||
|
||||
for i, input1 in enumerate(s):
|
||||
if i == 0 and not comps[i].isRunning():
|
||||
|
||||
14
day11.py
14
day11.py
@ -24,12 +24,12 @@ class Day(AOCDay):
|
||||
hull = Grid()
|
||||
face = 0
|
||||
pos = Coordinate(0, 0)
|
||||
painted = {}
|
||||
painted = set()
|
||||
|
||||
while not comp.isHalted():
|
||||
comp.addInput(hull.isSet(pos))
|
||||
comp.addInput(int(hull.isSet(pos)))
|
||||
hull.set(pos, comp.getOutput())
|
||||
painted[pos] = True
|
||||
painted.add(pos)
|
||||
face += 1 if comp.getOutput() else -1
|
||||
pos = pos + MOVEMENTS[face % 4]
|
||||
|
||||
@ -50,13 +50,7 @@ class Day(AOCDay):
|
||||
face += 1 if comp.getOutput() else -1
|
||||
pos = pos + MOVEMENTS[face % 4]
|
||||
|
||||
hull.transform(GridTransformation.ROTATE_RIGHT)
|
||||
hull.transform(GridTransformation.FLIP_HORIZONTALLY)
|
||||
for x in range(hull.minX, hull.maxX + 1):
|
||||
for y in range(hull.minY, hull.maxY + 1):
|
||||
print("#" if hull.isSet(Coordinate(x, y)) else " ", end="")
|
||||
|
||||
print()
|
||||
hull.print(true_char='#', false_char=' ')
|
||||
|
||||
return "see image above"
|
||||
|
||||
|
||||
37
day12.py
37
day12.py
@ -20,10 +20,20 @@ class Moon:
|
||||
self.y = y
|
||||
self.z = z
|
||||
|
||||
def getKineticEnergy(self):
|
||||
return abs(self.vel_x) + abs(self.vel_y) + abs(self.vel_z)
|
||||
|
||||
def getPotentialEnergy(self):
|
||||
return abs(self.x) + abs(self.y) + abs(self.z)
|
||||
|
||||
def getEnergy(self):
|
||||
potential = abs(self.x) + abs(self.y) + abs(self.z)
|
||||
kinetic = abs(self.vel_x) + abs(self.vel_y) + abs(self.vel_z)
|
||||
return potential * kinetic
|
||||
return self.getPotentialEnergy() * self.getKineticEnergy()
|
||||
|
||||
def __str__(self):
|
||||
return "x=%3d y=%3d z=%3d" % (self.x, self.y, self.z)
|
||||
|
||||
def __repr__(self):
|
||||
return str(self)
|
||||
|
||||
|
||||
def moveMoons(moons: List[Moon]):
|
||||
@ -50,7 +60,7 @@ class Day(AOCDay):
|
||||
(12644, "input12")
|
||||
],
|
||||
[
|
||||
# ??? (2772, "test_input12"),
|
||||
(2772, "test_input12"),
|
||||
(4686774924, "test_input12_2"),
|
||||
(None, "input12")
|
||||
]
|
||||
@ -66,21 +76,20 @@ class Day(AOCDay):
|
||||
|
||||
def part2(self) -> Any:
|
||||
moons = [Moon(*map(int, findall(scanline_regex, line)[0])) for line in self.getInput()]
|
||||
|
||||
init_moons = moons.copy()
|
||||
vel_0_pos = [0, 0, 0, 0]
|
||||
init_moons = [Moon(*map(int, findall(scanline_regex, line)[0])) for line in self.getInput()]
|
||||
vel_0_pos = [0] * len(moons)
|
||||
moveCounter = 0
|
||||
#while 0 in vel_0_pos:
|
||||
for bla in range(3000):
|
||||
while 0 in vel_0_pos:
|
||||
moveCounter += 1
|
||||
moveMoons(moons)
|
||||
for i, m in enumerate(moons):
|
||||
if m.x == init_moons[i].x and m.y == init_moons[i].y and m.z == init_moons[i].z and m.vel_x == 0 and m.vel_y == 0 and m.vel_z == 0:
|
||||
print(i, moveCounter)
|
||||
if (vel_0_pos[i] == 0 or vel_0_pos[i] > moveCounter - vel_0_pos[i]) and m.vel_x == 0 and m.vel_y == 0 and m.vel_z == 0:
|
||||
vel_0_pos[i] = moveCounter - vel_0_pos[i]
|
||||
if m.x == init_moons[i].x and m.y == init_moons[i].y and m.z == init_moons[i].z:
|
||||
# if i == 1:
|
||||
# print("init pos:", i, "after", moveCounter, "moves =>", m.getPotentialEnergy(), m.getKineticEnergy())
|
||||
if m.getKineticEnergy() == 0:
|
||||
print("init state:", i, "after", moveCounter, "moves =>", m.getPotentialEnergy())
|
||||
vel_0_pos[i] = moveCounter
|
||||
|
||||
print(vel_0_pos)
|
||||
return lcm(*vel_0_pos)
|
||||
|
||||
|
||||
|
||||
57
intcode.py
57
intcode.py
@ -1,7 +1,8 @@
|
||||
import threading
|
||||
import time
|
||||
from collections import deque, defaultdict
|
||||
from enum import Enum
|
||||
from queue import Queue
|
||||
from typing import List, Union
|
||||
from typing import List
|
||||
|
||||
|
||||
class IntCodeState(Enum):
|
||||
@ -10,26 +11,35 @@ class IntCodeState(Enum):
|
||||
HALTED = 2
|
||||
|
||||
|
||||
def _get_from_queue(queue: deque, count: int = 1, timeout: int = 10) -> int | List[int] | None:
|
||||
started = time.perf_counter()
|
||||
while len(queue) < count:
|
||||
time.sleep(0.0001)
|
||||
if time.perf_counter() - started > timeout:
|
||||
raise TimeoutError()
|
||||
|
||||
if count == 1:
|
||||
return queue.popleft()
|
||||
else:
|
||||
return [queue.popleft() for _ in range(count)]
|
||||
|
||||
|
||||
class IntCode(threading.Thread):
|
||||
def __init__(self, memory: List[int]):
|
||||
super().__init__()
|
||||
self.instr_ptr = 0
|
||||
self.memory = memory
|
||||
self.input_queue = Queue()
|
||||
self.output_queue = Queue()
|
||||
self.memory = defaultdict(int)
|
||||
for i, v in enumerate(memory):
|
||||
self.memory[i] = v
|
||||
self.input_queue = deque()
|
||||
self.output_queue = deque()
|
||||
self.state = IntCodeState.INITIALIZED
|
||||
self.relative_base = 0
|
||||
|
||||
def getMemoryValue(self, address: int) -> int:
|
||||
if address > len(self.memory) - 1:
|
||||
self.memory.extend([0] * (address - len(self.memory) + 1))
|
||||
|
||||
return self.memory[address]
|
||||
|
||||
def setMemoryValue(self, address: int, value: int):
|
||||
if address > len(self.memory) - 1:
|
||||
self.memory.extend([0] * (address - len(self.memory) + 1))
|
||||
|
||||
self.memory[address] = value
|
||||
|
||||
def getParameterValue(self, address: int, mode: int = 0) -> int:
|
||||
@ -52,26 +62,20 @@ class IntCode(threading.Thread):
|
||||
def isHalted(self):
|
||||
return self.state == IntCodeState.HALTED
|
||||
|
||||
def sendOutputTo(self, target_queue: Queue):
|
||||
def sendOutputTo(self, target_queue: deque):
|
||||
self.output_queue = target_queue
|
||||
|
||||
def addInput(self, value: int):
|
||||
self.input_queue.put(value)
|
||||
self.input_queue.append(value)
|
||||
|
||||
def hasOutput(self):
|
||||
return self.output_queue.qsize() > 0
|
||||
return len(self.output_queue) > 0
|
||||
|
||||
def getOutput(self, count: int = 1, block: bool = True, timeout: int = None) -> Union[int, List[int]]:
|
||||
if count == 1:
|
||||
res = self.output_queue.get(block=block, timeout=timeout)
|
||||
self.output_queue.task_done()
|
||||
else:
|
||||
res = []
|
||||
for _ in range(count):
|
||||
res.append(self.output_queue.get(block=block, timeout=timeout))
|
||||
self.output_queue.task_done()
|
||||
def getOutput(self, count: int = 1, timeout: int = 10) -> int | List[int] | None:
|
||||
return _get_from_queue(self.output_queue, count, timeout)
|
||||
|
||||
return res
|
||||
def getInput(self, count: int = 1, timeout: int = 10) -> int | List[int] | None:
|
||||
return _get_from_queue(self.input_queue, count, timeout)
|
||||
|
||||
def run(self):
|
||||
self.state = IntCodeState.RUNNING
|
||||
@ -96,11 +100,10 @@ class IntCode(threading.Thread):
|
||||
self.instr_ptr += 4
|
||||
elif op_code == 3: # input
|
||||
target_addr = self.getTargetAddress(self.instr_ptr + 1, p1_mode)
|
||||
self.setMemoryValue(target_addr, self.input_queue.get(timeout=30))
|
||||
self.input_queue.task_done()
|
||||
self.setMemoryValue(target_addr, self.getInput())
|
||||
self.instr_ptr += 2
|
||||
elif op_code == 4: # output
|
||||
self.output_queue.put(self.getParameterValue(self.instr_ptr + 1, p1_mode))
|
||||
self.output_queue.append(self.getParameterValue(self.instr_ptr + 1, p1_mode))
|
||||
self.instr_ptr += 2
|
||||
elif op_code == 5: # jump-if-true
|
||||
if self.getParameterValue(self.instr_ptr + 1, p1_mode) != 0:
|
||||
|
||||
Loading…
Reference in New Issue
Block a user