Code for the Advent of Code event
aoc advent-of-code
at main 46 lines 1.4 kB view raw
1people = {} 2 3parse = (line) -> 4 name, mod, amount, other = line\match '^(%w+) would (%w+) (%d+) happiness units by sitting next to (%w+)%.$' 5 6 change = (mod == 'gain' and 1 or -1) * amount 7 8 people[name] = {} unless people[name] 9 people[name][other] = change 10 11generate_permutations = (list, length) -> 12 coroutine.yield list if length == 0 13 14 for i = 1, length 15 list[length], list[i] = list[i], list[length] 16 generate_permutations list, length - 1 17 list[length], list[i] = list[i], list[length] 18 19permutations = (list) -> 20 length = table.getn list 21 coroutine.wrap -> generate_permutations list, length 22 23get_happiness = (order) -> 24 happiness = 0 25 for index, person in ipairs order 26 happiness += people[person][order[index == 1 and #order or index - 1]] 27 happiness += people[person][order[index == #order and 1 or index + 1]] 28 happiness 29 30get_max_happiness = -> 31 names = [k for k, _ in pairs people] 32 values = [get_happiness perm for perm in permutations names] 33 max = values[1] 34 for i = 2, #values 35 max = values[i] if values[i] > max 36 max 37 38add_self = -> 39 people.__SELF__ = {} 40 for name, _ in pairs people 41 unless name == '__SELF__' 42 people.__SELF__[name] = 0 43 people[name].__SELF__ = 0 44 45 46{ :parse, :get_max_happiness, :add_self }