advent_of_code_2022

My (attempted) solutions to the 2022 Advent of Code
git clone https://git.eamoncaddigan.net/advent_of_code_2022.git
Log | Files | Refs | README

day_20.jl (2127B)


      1 #!/usr/bin/env julia
      2 # https://adventofcode.com/2022/day/20
      3 using AdventOfCode
      4 
      5 example = readlines(IOBuffer("""
      6     1
      7     2
      8     -3
      9     3
     10     -2
     11     0
     12     4"""))
     13 input = readlines("data/day_20.txt")
     14 
     15 mutable struct CoordFile
     16     values::Vector{Int}
     17     indices::Vector{Int}
     18 end
     19 
     20 CoordFile(x::Vector{Int}) = CoordFile(x, collect(0:length(x)-1))
     21 
     22 CoordFile(input::Vector{<:AbstractString}) = CoordFile(parse.(Int, input))
     23 
     24 """
     25 Return an Array of the elements in order.
     26 """
     27 Base.collect(coordfile::CoordFile) = coordfile.values[sortperm(coordfile.indices)]
     28 
     29 Base.length(coordfile::CoordFile) = length(coordfile.values)
     30 
     31 function Base.getindex(coordfile::CoordFile, i)
     32     coordfile.values[findfirst(x->x==i, coordfile.indices)]
     33 end
     34 
     35 """
     36 Move an element
     37 """
     38 function moveelement!(coordfile::CoordFile, index::Int)
     39     oldindex = coordfile.indices[index]
     40     newindex = oldindex +
     41                mod(coordfile.values[index], length(coordfile) - 1)
     42     if newindex >= length(coordfile)
     43         newindex -= length(coordfile) - 1
     44     end
     45     for i = eachindex(coordfile.indices)
     46         if coordfile.indices[i] > oldindex
     47             coordfile.indices[i] -= 1
     48         end
     49         if coordfile.indices[i] >= newindex
     50             coordfile.indices[i] += 1
     51         end
     52     end
     53     coordfile.indices[index] = newindex
     54     coordfile
     55 end
     56 
     57 function mixelements!(coordfile::CoordFile)
     58     for i = 1:length(coordfile)
     59         moveelement!(coordfile, i)
     60     end
     61     coordfile
     62 end
     63 
     64 function coordinates(coordfile::CoordFile)
     65     # Find the zero
     66     zeroloc = coordfile.indices[findfirst(x->x==0, coordfile.values)]
     67     mapreduce(x->coordfile[mod(zeroloc + x, length(coordfile))],
     68               +,
     69               1000:1000:3000)
     70 end
     71 
     72 function part_1(input)
     73     input |> CoordFile |> mixelements! |> coordinates
     74 end
     75 @assert part_1(example) == 3
     76 @info part_1(input)
     77 
     78 function part_2(input)
     79     coordfile = CoordFile(input)
     80     for i = 1:length(coordfile)
     81         coordfile.values[i] *= 811589153
     82     end
     83     for i = 1:10
     84         mixelements!(coordfile)
     85     end
     86     coordinates(coordfile)
     87 end
     88 @assert part_2(example) == 1623178306
     89 @info part_2(input)