parent
f871f28d27
commit
762e65126a
@ -1,25 +1,42 @@
|
|||||||
instructions = ARGF.read.lines(chomp: true)
|
instructions = ARGF.read.lines(chomp: true)
|
||||||
|
|
||||||
adds = {}
|
def exec(instructions)
|
||||||
cycle = 1
|
return enum_for(__method__, instructions) unless block_given?
|
||||||
instructions.each do |instruction|
|
|
||||||
cycle += case instruction
|
x = 1
|
||||||
when /noop/
|
instructions.each do |instruction|
|
||||||
1
|
case instruction
|
||||||
when /addx (-?\d+)/
|
when /noop/
|
||||||
adds[cycle+1] = $1.to_i
|
yield x
|
||||||
2
|
when /addx (-?\d+)/
|
||||||
else fail instruction
|
yield x
|
||||||
end
|
yield x
|
||||||
|
x += $1.to_i
|
||||||
|
else
|
||||||
|
fail "invalid instruction: #{instruction}"
|
||||||
|
end
|
||||||
|
end
|
||||||
|
yield x
|
||||||
end
|
end
|
||||||
|
|
||||||
xs = (0..adds.keys.max).inject([1]) { _1 << _1.last + adds.fetch(_2, 0) }
|
x_hist = exec(instructions).to_a
|
||||||
p 20.step(by: 40, to: 220).map { [_1, xs[_1]] }.sum { _1 * _2 }
|
|
||||||
|
# part one
|
||||||
|
p 20.step(by: 40, to: 220).sum { x_hist[_1-1] * _1 }
|
||||||
|
|
||||||
puts 6.times.map {|y|
|
# part two
|
||||||
40.times.map {|x|
|
puts x_hist.each_slice(40).map {|row|
|
||||||
cycle = 40*y + x + 1
|
row.each.with_index.map {|x, cycle|
|
||||||
xx = xs.fetch(cycle, xs.last)
|
(-1..1).cover?(cycle - x) ? ?# : ?.
|
||||||
(-1..1).cover?(x - xx) ? ?# : ?.
|
|
||||||
}.join
|
}.join
|
||||||
}.join("\n")
|
}.join("\n")
|
||||||
|
|
||||||
|
# a functional version of part two, but I think
|
||||||
|
# the imperative version feels closer to the domain
|
||||||
|
#
|
||||||
|
# x_hist.each_slice(40) do |row|
|
||||||
|
# row.each.with_index do |x, cycle|
|
||||||
|
# putc (-1..1).cover?(cycle - x) ? ?# : ?.
|
||||||
|
# end
|
||||||
|
# puts
|
||||||
|
# end
|
||||||
|
@ -0,0 +1,30 @@
|
|||||||
|
require "minitest/autorun"
|
||||||
|
|
||||||
|
def exec(instructions)
|
||||||
|
return enum_for(__method__, instructions) unless block_given?
|
||||||
|
|
||||||
|
x = 1
|
||||||
|
instructions.each do |instruction|
|
||||||
|
case instruction
|
||||||
|
when /noop/
|
||||||
|
yield x
|
||||||
|
when /addx (-?\d+)/
|
||||||
|
yield x
|
||||||
|
yield x
|
||||||
|
x += $1.to_i
|
||||||
|
else
|
||||||
|
fail "invalid instruction: #{instruction}"
|
||||||
|
end
|
||||||
|
end
|
||||||
|
yield x
|
||||||
|
end
|
||||||
|
|
||||||
|
class TestDay10 < Minitest::Test
|
||||||
|
def test_example
|
||||||
|
assert_equal [1, 1, 1, 4, 4, -1], exec(<<~PROG.lines(chomp: true)).to_a
|
||||||
|
noop
|
||||||
|
addx 3
|
||||||
|
addx -5
|
||||||
|
PROG
|
||||||
|
end
|
||||||
|
end
|
Loading…
Reference in new issue