Advent of Code, Day 19

Day 19 of Advent of Code is here! This one was tough. I got my code working against the example, but when that was taking over 10 mins to complete with my data, I decided to go searching for someone else’s example.

I found this example that I copied, thank you eQueline! This is really impressive as it uses regex and it’s remarkably fast. I started thinking down this road, but found it too complex to do, but happy this person was more capable than me ;)

See all of my other solutions here. If you’re interested, check out what my colleagues at Slalom are doing with their Advent of Code! You can see this and my other solutions on github.

Day 19: Monster Messages

Part I & II

The code I copied does both parts 1 and 2 in the same script, and it’s super fast. But first, here’s our data:

And the code!

//ref https://github.com/eQueline/Advent-of-Code-2020/blob/main/AoC%2019.js
const fs = require('fs');

console.log('Start');

let testInput = fs.readFileSync('./input.txt', 'utf-8').trim()

var input = testInput.split('\n\n').map(a => a.split('\n'));
var messages = input[1];
var rules = [];
input[0].forEach(a=>rules[a.split(': ')[0]] = a.split(': ')[1]);
rules = rules.map(a=>a.replace(/"/g,''));

function expandAll(str) {
    while (str.match(/\d/)) {
        let expList = (str.match(/(?<!\d)\d+(?!\d)/g) || []);
        expList = expList.filter((a,i,ar)=>ar.findIndex(b=>b==a)==i);
        expList.forEach((exp)=>{
            str = str.replace(new RegExp(`(?<!\\d)${exp}(?!\\d)`, 'g'), (rules[exp].includes('|')?(`(${rules[exp]})`):rules[exp]));
        });
    }
    return str.replace(/\s/g, '');
}

// 0: 8 11
// 8: 42
// 11: 42 31
// 0:= 42{2} 31
var rule42 = expandAll('42');
console.log('Expanded 42');
var rule31 = expandAll('31');
console.log('Expanded 31');
var loopRule = new RegExp(`^${rule42}{2}${rule31}$`);
console.log(`Answer 1: ${messages.filter(a=>loopRule.test(a)).length}`);

// 0: 8 11
// 8: 42 | 42 8
// 11: 42 31 | 42 11 31
// 0:= 42+ 42{i} 31{i}
var valid = [];
for (let i=1; i<5; i++) {
    loopRule = new RegExp(`^${rule42}+${rule42}{${i}}${rule31}{${i}}$`);
    valid.push(...messages.filter(a=>!valid.includes(a)&&loopRule.test(a)));
}
console.log(`Answer 2: ${valid.length}`);

So good!

How did it go for you?

Did you find the answer on your own? How did you do it? Anything stump you? I’d love to hear how you did! Please comment below! I have also loaded up just the challenge and code from this and my other days on github, you can follow along there too: pretty Git pages or the code in the repo.

One thought on “Advent of Code, Day 19

Add yours

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

Create a free website or blog at WordPress.com.

Up ↑

%d bloggers like this: