Skip to content

Commit 920ff55

Browse files
feat(2020-day-07): recursively find all bag colors that allow specified child bag
1 parent 8ec6621 commit 920ff55

File tree

2 files changed

+51
-3
lines changed

2 files changed

+51
-3
lines changed

2020/day-7/bagRules.js

Lines changed: 32 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,9 @@ const parseRule = (rule) => {
88
result.inner = outRemainder[0].split(', ').map((str) => {
99
const inRemainder = str.split(' ')
1010
const count = Number(inRemainder.shift())
11-
const color = inRemainder.join(' ').replace('s.', '')
11+
const color = inRemainder.join(' ')
12+
.replace('.', '')
13+
.replace('bags', 'bag')
1214
return {
1315
count,
1416
color
@@ -19,6 +21,34 @@ const parseRule = (rule) => {
1921
return result
2022
}
2123

24+
const findAllowedOuter = (rules, color) => {
25+
const allowed = {}
26+
27+
// Loop through the rules, find all colors this bag is allowed within
28+
rules.filter((rule) => {
29+
// console.debug(rule)
30+
if (!rule.inner) { return false }
31+
// match when inners contain the color
32+
return (
33+
rule.inner &&
34+
rule.inner.filter((child) => {
35+
return (child.color === color)
36+
}).length > 0
37+
)
38+
}).forEach((rule) => {
39+
allowed[rule.outer] = true
40+
})
41+
42+
// Take the list of allowed colors, and find out which they are allowed within
43+
Object.keys(allowed).forEach((color) => {
44+
// Recursively loop
45+
Object.assign(allowed, findAllowedOuter(rules, color))
46+
})
47+
48+
return allowed
49+
}
50+
2251
module.exports = {
23-
parseRule
52+
parseRule,
53+
findAllowedOuter
2454
}

2020/day-7/bagRules.test.js

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
/* eslint-env mocha */
22
const { expect } = require('chai')
3-
const { parseRule } = require('./bagRules')
3+
const { parseRule, findAllowedOuter } = require('./bagRules')
44

55
const testData = {
66
rules: [
@@ -39,5 +39,23 @@ describe('--- Day 7: Handy Haversacks ---', () => {
3939
})
4040
})
4141
})
42+
describe('findAllowedOuter()', () => {
43+
it('list bags the specified bag is allowed to be placed in', () => {
44+
const expectedColors = [
45+
'bright white bag',
46+
'muted yellow bag',
47+
'dark orange bag',
48+
'light red bag'
49+
]
50+
const result = findAllowedOuter(
51+
testData.rules.map(parseRule),
52+
'shiny gold bag'
53+
)
54+
expectedColors.forEach(color => {
55+
expect(result[color]).to.equal(true)
56+
})
57+
expect(Object.keys(result).length).to.equal(expectedColors.length)
58+
})
59+
})
4260
})
4361
})

0 commit comments

Comments
 (0)