Solve a few more puzzles.
This commit is contained in:
parent
161ee6e244
commit
8a7eab81e0
72
day10.cr
Normal file
72
day10.cr
Normal file
@ -0,0 +1,72 @@
|
||||
require "advent"
|
||||
|
||||
struct Tuple(*T)
|
||||
def reduce_fraction
|
||||
gcd = (self[0].gcd self[1]).abs
|
||||
return self if gcd == 0
|
||||
{self[0] // gcd, self[1]//gcd}
|
||||
end
|
||||
end
|
||||
|
||||
struct Tuple(*T)
|
||||
def -(other)
|
||||
{self[0]-other[0], self[1] - other[1]}
|
||||
end
|
||||
|
||||
def dist
|
||||
self[0] + self[1]
|
||||
end
|
||||
end
|
||||
|
||||
input = input(2019, 10)
|
||||
asteroids = Set({Int32, Int32}).new
|
||||
input.lines.each_with_index do |l, y|
|
||||
l.chars.each_with_index do |c, x|
|
||||
next unless c == '#'
|
||||
asteroids << {x, y}
|
||||
end
|
||||
end
|
||||
|
||||
p1 = asteroids.max_of do |a|
|
||||
angles = Set({Int32, Int32}).new
|
||||
asteroids.each do |b|
|
||||
next if a == b
|
||||
angles << (b-a).reduce_fraction
|
||||
end
|
||||
angles.size
|
||||
end
|
||||
|
||||
puts p1
|
||||
|
||||
p2s = asteroids.max_by do |a|
|
||||
angles = Set({Int32, Int32}).new
|
||||
asteroids.each do |b|
|
||||
next if a == b
|
||||
angles << (b-a).reduce_fraction
|
||||
end
|
||||
angles.size
|
||||
end
|
||||
|
||||
angle_groups = asteroids.group_by do |a|
|
||||
(a - p2s).reduce_fraction
|
||||
end
|
||||
angle_groups.delete({0,0})
|
||||
angle_groups.each do |k, v|
|
||||
v.sort! do |a|
|
||||
(a - p2s).dist
|
||||
end
|
||||
end
|
||||
|
||||
angles = angle_groups.keys.sort_by do |k|
|
||||
-Math.atan2(k[0].to_f32, k[1].to_f32)
|
||||
end
|
||||
i = 1
|
||||
angles.cycle do |angle|
|
||||
next if angle_groups[angle].empty?
|
||||
asteroid = angle_groups[angle].delete_at(0)
|
||||
if i == 200
|
||||
puts asteroid[0] * 100 + asteroid[1]
|
||||
break
|
||||
end
|
||||
i += 1
|
||||
end
|
42
day11.cr
Normal file
42
day11.cr
Normal file
@ -0,0 +1,42 @@
|
||||
require "advent"
|
||||
require "./intcode_fibers.cr"
|
||||
|
||||
painted_white = Set({Int64, Int64}).new
|
||||
color = {} of {Int64,Int64} => Int64
|
||||
color[{0_i64, 0_i64}] = 1_i64
|
||||
input, output = new_interpreter("", input(2019, 11).split(",").map &.to_i64)
|
||||
pos = {0_i64, 0_i64}
|
||||
facing = {0_i64, 1_i64}
|
||||
|
||||
struct Tuple(*T)
|
||||
def turn_left
|
||||
{-self[1], self[0]}
|
||||
end
|
||||
|
||||
def turn_right
|
||||
turn_left.turn_left.turn_left
|
||||
end
|
||||
|
||||
def add(other)
|
||||
{self[0] + other[0], self[1] + other[1]}
|
||||
end
|
||||
end
|
||||
|
||||
loop do
|
||||
c = color[pos]? || 0_i64
|
||||
input.send c
|
||||
break unless nc = output.receive
|
||||
break unless turn = output.receive
|
||||
color[pos] = nc
|
||||
painted_white << pos if nc == 1
|
||||
facing = (turn == 0 ? facing.turn_left : facing.turn_right)
|
||||
pos = pos.add facing
|
||||
end
|
||||
|
||||
6.times do |y|
|
||||
y = - y
|
||||
45.times do |x|
|
||||
print (color[{x.to_i64, y.to_i64}]? == 1 ? '#' : ' ')
|
||||
end
|
||||
puts
|
||||
end
|
6
day7.cr
6
day7.cr
@ -1,18 +1,18 @@
|
||||
require "./intcode.cr"
|
||||
require "./intcode_fibers.cr"
|
||||
|
||||
prog = File.read("day7.txt").chomp.split(",").map(&.to_i32)
|
||||
prog = File.read("day7.txt").chomp.split(",").map(&.to_i64)
|
||||
|
||||
def chain_amplifiers(prog, perm, loop = false)
|
||||
chans = perm.map { |f| new_interpreter(f, prog) }
|
||||
chans.zip perm do |amp, freq|
|
||||
amp[0].send freq
|
||||
amp[0].send freq.to_i64
|
||||
end
|
||||
|
||||
chans[0][0].send 0
|
||||
|
||||
i = 0
|
||||
history = Array(Int32).new(chans.size, 0)
|
||||
history = Array(Int64).new(chans.size, 0)
|
||||
loop do
|
||||
j = (i+1) % chans.size
|
||||
break unless received = chans[i][1].receive
|
||||
|
19
day8.cr
Normal file
19
day8.cr
Normal file
@ -0,0 +1,19 @@
|
||||
require "advent"
|
||||
|
||||
input = input(2019, 8).chomp
|
||||
layers = input.chars.each_slice(25*6).to_a
|
||||
layer = layers.min_by(&.count('0'))
|
||||
puts(layer.count('2') * layer.count('1'))
|
||||
|
||||
message = layers.reduce do |l1, l2|
|
||||
l1.zip_with(l2) do |a1, a2|
|
||||
next (a1 == '2') ? a2 : a1
|
||||
end
|
||||
end
|
||||
|
||||
6.times do |i|
|
||||
25.times do |j|
|
||||
print(message[25*i+j] == '1' ? '#' : ' ')
|
||||
end
|
||||
puts
|
||||
end
|
7
day9.cr
Normal file
7
day9.cr
Normal file
@ -0,0 +1,7 @@
|
||||
require "advent"
|
||||
require "./intcode_fibers.cr"
|
||||
|
||||
input = input(2019, 9).split(",").map &.to_i64
|
||||
input, output = new_interpreter("", input)
|
||||
input.send 2_i64
|
||||
puts output.receive
|
@ -1,40 +1,59 @@
|
||||
def new_interpreter(f, prog)
|
||||
prog = prog.clone
|
||||
input = Channel(Int32).new
|
||||
output = Channel(Int32?).new
|
||||
def new_interpreter(f, p)
|
||||
prog = {} of Int64 => Int64
|
||||
p.each_with_index do |v, i|
|
||||
prog[i.to_i64] = v.to_i64
|
||||
end
|
||||
|
||||
input = Channel(Int64).new
|
||||
output = Channel(Int64?).new
|
||||
spawn do
|
||||
op = ""
|
||||
pc = 0
|
||||
arg = ->(i : Int32) { op[-(3+i)] == '0' ? prog[prog[pc+1+i]] : prog[pc+1+i] }
|
||||
pc = 0_i64
|
||||
base = 0_i64
|
||||
index = ->(i : Int32) {
|
||||
case op[-(3+i)]
|
||||
when '0'
|
||||
prog[pc+1+i]
|
||||
when '1'
|
||||
pc+1+i
|
||||
else
|
||||
prog[pc+1+i] + base
|
||||
end
|
||||
}
|
||||
get = ->(i : Int32) { prog[index.call(i)]? || 0_i64 }
|
||||
set = ->(i : Int32, v : Int64) { prog[index.call(i)] = v }
|
||||
loop do
|
||||
op = "0000" + prog[pc].to_s
|
||||
case op
|
||||
when .ends_with? "1"
|
||||
prog[prog[pc+3]] = arg.call(0) + arg.call(1)
|
||||
set.call(2, get.call(0) + get.call(1))
|
||||
pc += 4
|
||||
when .ends_with? "2"
|
||||
prog[prog[pc+3]] = arg.call(0) * arg.call(1)
|
||||
set.call(2, get.call(0) * get.call(1))
|
||||
pc += 4
|
||||
when .ends_with? "3"
|
||||
prog[prog[pc+1]] = input.receive
|
||||
set.call(0, input.receive)
|
||||
pc += 2
|
||||
when .ends_with? "4"
|
||||
output.send(arg.call(0))
|
||||
output.send(get.call(0))
|
||||
pc += 2
|
||||
when .ends_with? "5"
|
||||
pc = arg.call(0) != 0 ? arg.call(1) : pc + 3
|
||||
pc = get.call(0) != 0 ? get.call(1) : pc + 3
|
||||
when .ends_with? "6"
|
||||
pc = arg.call(0) == 0 ? arg.call(1) : pc + 3
|
||||
pc = get.call(0) == 0 ? get.call(1) : pc + 3
|
||||
when .ends_with? "7"
|
||||
prog[prog[pc+3]] = arg.call(0) < arg.call(1) ? 1 : 0
|
||||
set.call(2, get.call(0) < get.call(1) ? 1_i64 : 0_i64)
|
||||
pc += 4
|
||||
when .ends_with? "8"
|
||||
prog[prog[pc+3]] = arg.call(0) == arg.call(1) ? 1 : 0
|
||||
set.call(2, get.call(0) == get.call(1) ? 1_i64 : 0_i64)
|
||||
pc += 4
|
||||
when .ends_with? "99"
|
||||
input.receive
|
||||
output.send(nil)
|
||||
break
|
||||
when .ends_with? "9"
|
||||
base += get.call(0)
|
||||
pc += 2
|
||||
end
|
||||
end
|
||||
end
|
||||
|
Loading…
Reference in New Issue
Block a user