day-12.jl (1708B)
1 function evolve!(coord, velocity)
2 # Computes velocity caused by given coordinates, move them in corresponding
3 # directions, and return the velocity vector.
4 for i in 1:size(coord, 1)
5 for j in (i + 1):size(coord, 1)
6 dv = sign.(coord[j, :] - coord[i, :])
7 velocity[i, :] += dv
8 velocity[j, :] -= dv
9 end
10 end
11 end
12
13 function calc_energy(coord, velocity)
14 pot = sum(abs.(coord); dims = 2)
15 kin = sum(abs.(velocity); dims = 2)
16 sum(pot .* kin)
17 end
18
19 function part_1(input)
20 coord = copy(input)
21 velocity = zeros(size(coord))
22 for i in 1:1000
23 evolve!(coord, velocity)
24 coord += velocity
25 end
26 Int(calc_energy(coord, velocity))
27 end
28
29 function calc_period(coord)
30 coord = copy(coord)
31 velocity = zeros(size(coord))
32 i = 0
33 abs_speed_sum = 1
34 # Cycle reaches half point when all speed reaches 0.
35 while abs_speed_sum != 0
36 evolve!(coord, velocity)
37 coord += velocity
38 abs_speed_sum = sum(abs.(velocity))
39 i += 1
40 end
41 i * 2
42 end
43
44 function part_2(input)
45 # Each direction should be independent and have their own cycles.
46 # So get the period in each direction and find least common multiplier.
47 period_x = calc_period(input[:, 1])
48 period_y = calc_period(input[:, 2])
49 period_z = calc_period(input[:, 3])
50 lcm(period_x, period_y, period_z)
51 end
52
53 input = reshape(collect(Iterators.flatten(map(readlines(open("input.txt"))) do line
54 map(x -> parse(Int, x),
55 match(r"<x=(-?[0-9]+), y=(-?[0-9]+), z=(-?[0-9]+)", line).captures)
56 end)), (3, :)) |> transpose
57
58 println("Julia:")
59 println("Part 1: ", part_1(input))
60 println("Part 2: ", part_2(input))