121 lines
2.1 KiB
Crystal
121 lines
2.1 KiB
Crystal
require "./common.cr"
|
|
|
|
lines = File.read("day13_input").split "\n"
|
|
lines.pop
|
|
|
|
map = lines.map &.chars
|
|
carts = [] of Tuple(Int32, Int32, Char, Char)
|
|
|
|
map.each_with_index do |line, y|
|
|
line.each_with_index do |char, x|
|
|
carts << {x, y, char, 'l'} if char == '>' || char == '<' || char == '^' || char == 'v'
|
|
end
|
|
end
|
|
|
|
def next_turn(char)
|
|
return 'r' if char == 's'
|
|
return 'l' if char == 'r'
|
|
return 's'
|
|
end
|
|
|
|
def turn_dir(char, turn)
|
|
if turn == 'l'
|
|
return '<' if char == '^'
|
|
return 'v' if char == '<'
|
|
return '>' if char == 'v'
|
|
return '^' if char == '>'
|
|
end
|
|
if turn == 'r'
|
|
return '>' if char == '^'
|
|
return '^' if char == '<'
|
|
return '<' if char == 'v'
|
|
return 'v' if char == '>'
|
|
end
|
|
return char
|
|
end
|
|
|
|
def offset(char)
|
|
case char
|
|
when '^'
|
|
{0, -1}
|
|
when 'v'
|
|
{0, 1}
|
|
when '<'
|
|
{-1, 0}
|
|
when '>'
|
|
{1, 0}
|
|
else
|
|
{0, 0}
|
|
end
|
|
end
|
|
|
|
def turn(cart, turnchar)
|
|
if turnchar == '/'
|
|
return '>' if cart == '^'
|
|
return 'v' if cart == '<'
|
|
return '^' if cart == '>'
|
|
return '<'
|
|
elsif turnchar == '\\'
|
|
return 'v' if cart == '>'
|
|
return '<' if cart == '^'
|
|
return '^' if cart == '<'
|
|
return '>'
|
|
end
|
|
return cart
|
|
end
|
|
|
|
def simulate(map, carts)
|
|
crashed = [] of Int32
|
|
crashed_pos = [] of Tuple(Int32, Int32)
|
|
|
|
carts.sort_by! do |cart|
|
|
x, y, c, t = cart
|
|
y * 280 + x
|
|
end
|
|
|
|
carts.each_with_index do |cart, index|
|
|
next if crashed.includes? index
|
|
x, y, c, t = cart
|
|
|
|
# TRUSTED
|
|
dx, dy = offset(c)
|
|
x += dx
|
|
y += dy
|
|
if map[y][x] == '+'
|
|
c = turn_dir(c, t)
|
|
t = next_turn(t)
|
|
else
|
|
c = turn(c, map[y][x])
|
|
end
|
|
# UNTRUSTED
|
|
|
|
carts.each_with_index do |c2, i2|
|
|
next if crashed.includes? i2
|
|
next if (c2[0] != x) || (c2[1] != y)
|
|
|
|
puts carts
|
|
crashed << index
|
|
crashed << i2
|
|
crashed_pos << {x, y}
|
|
end
|
|
|
|
carts[index] = {x, y, c, t}
|
|
end
|
|
|
|
crashed.sort!.reverse!.uniq!.each do |index|
|
|
carts.delete_at index
|
|
end
|
|
|
|
unless crashed_pos.empty?
|
|
puts crashed_pos
|
|
end
|
|
|
|
return carts.size <= 1
|
|
end
|
|
|
|
count = 0
|
|
while !simulate(map, carts)
|
|
count += 1
|
|
end
|
|
puts carts[0]?
|