advent-of-code/12022/09/09_2.lua

90 lines
2.1 KiB
Lua

io.input("test2")
io.input("input")
function pos2index( pos )
return pos.x*10000 + pos.y
end
function constrain( n, min, max )
-- returns converted n, and if it was converted
local min = min or -1
local max = max or 1
if n < min then return min, true
elseif n > max then return max, true
else return n, false
end
end
local head = { x=1, y=1 }
local n = 9
local tail = {}
for i=1,n do tail[i] = { x=1, y=1 } end
local visitedP1 = { [pos2index(tail[1])] = true }
local visitedP2 = { [pos2index(tail[n])] = true }
local resultP1 = 1
local resultP2 = 1
for line in io.lines() do
local dir, q = string.match(line, "^(%a) (%d+)$")
q = tonumber(q)
for step = 1,q do
if dir == "R" then
head.x = head.x + 1
elseif dir == "L" then
head.x = head.x - 1
elseif dir == "U" then
head.y = head.y + 1
elseif dir == "D" then
head.y = head.y - 1
end
-- loop through tails
for i=1,n do
local h = head
if i>1 then h = tail[i-1] end
local t = tail[i]
local dif = { x=h.x-t.x, y=h.y-t.y }
-- gx, gy indicate if the abs diff was greater than 1
local dx, gx = constrain(dif.x)
local dy, gy = constrain(dif.y)
if dif.x == 0 and gy then -- vertical
t.y = t.y + dy
elseif dif.y == 0 and gx then -- horizontal
t.x = t.x + dx
elseif gx or gy then -- diagonal further away
t.y = t.y + dy
t.x = t.x + dx
end
end
-- part 1
local index = pos2index(tail[1])
if not visitedP1[index] then
visitedP1[index] = true
resultP1 = resultP1 + 1
end
-- part 2
local index = pos2index(tail[n])
if not visitedP2[index] then
visitedP2[index] = true
resultP2 = resultP2 + 1
end
-- visitedP1[ pos2index(tail[1]) ] = true
-- visitedP2[ pos2index(tail[n]) ] = true
end
end
print("part 1", resultP1)
print("part 2", resultP2)
local result = 0
for k, v in pairs(visitedP1) do
result = result + 1
end
print("part 1", result, resultP1)
local result = 0
for k, v in pairs(visitedP2) do
result = result + 1
end
print("part 2", result, resultP2)