Published
Edited
Dec 4, 2020
Insert cell
Insert cell
Insert cell
_ = require('lodash')
Insert cell
parseInput = i =>
i
.split('\n\n')
.map(p => p.split(/\s/).map(e => e.split(':')))
.map(_.fromPairs)
Insert cell
parseInput(testInput)
Insert cell
requiredFields = ['byr', 'iyr', 'eyr', 'hgt', 'hcl', 'ecl', 'pid']
Insert cell
validateRequiredFields = p => {
for (let field of requiredFields) {
if (!p[field]) return false;
}
return true;
}
Insert cell
parseInput(testInput).filter(validateRequiredFields)
Insert cell
Insert cell
Insert cell
parseInput(input).filter(validateRequiredFields).length
Insert cell
Insert cell
fieldValidators = ({
byr: function(y) {
if (!/^\d{4}$/.test(y)) return false;
if (parseInt(y) < 1920 || parseInt(y) > 2002) return false;
return true;
},
iyr: function(y) {
if (!/^\d{4}$/.test(y)) return false;
if (parseInt(y) < 2010 || parseInt(y) > 2020) return false;
return true;
},
eyr: function(y) {
if (!/^\d{4}$/.test(y)) return false;
if (parseInt(y) < 2020 || parseInt(y) > 2030) return false;
return true;
},
hgt: function(h) {
const matches = h.match(/^(\d+)(in|cm)$/);
if (!matches) return false;
const hgt = parseInt(matches[1]);
if (matches[2] == 'cm') {
if (hgt < 150 || hgt > 193) return false;
} else {
if (hgt < 59 || hgt > 76) return false;
}
return true;
},
hcl: function(hcl) {
return /^\#[0-9a-f]{6}$/.test(hcl);
},
ecl: function(ecl) {
return ['amb', 'blu', 'brn', 'gry', 'grn', 'hzl', 'oth'].includes(ecl);
},
pid: function(pid) {
return /^\d{9}$/.test(pid);
}
})
Insert cell
[fieldValidators.byr('2002'), fieldValidators.byr('2003')]
Insert cell
[
fieldValidators.hgt('60in'),
fieldValidators.hgt('190cm'),
fieldValidators.hgt('190in'),
fieldValidators.hgt('190')
]
Insert cell
[
fieldValidators.hcl('#123abc'),
fieldValidators.hcl('#123abz'),
fieldValidators.hcl('123abc')
]
Insert cell
[fieldValidators.ecl('brn'), fieldValidators.ecl('wat')]
Insert cell
[fieldValidators.pid('000000001'), fieldValidators.pid('0123456789')]
Insert cell
validateFields = passport => {
for (const field in fieldValidators) {
if (!fieldValidators[field](passport[field])) return false;
}
return true;
}
Insert cell
{
const invalidPassports = `eyr:1972 cid:100
hcl:#18171d ecl:amb hgt:170 pid:186cm iyr:2018 byr:1926

iyr:2019
hcl:#602927 eyr:1967 hgt:170cm
ecl:grn pid:012533040 byr:1946

hcl:dab227 iyr:2012
ecl:brn hgt:182cm pid:021572410 eyr:2020 byr:1992 cid:277

hgt:59cm ecl:zzz
eyr:2038 hcl:74454a iyr:2023
pid:3556412378 byr:2007`;
return parseInput(invalidPassports)
.filter(validateRequiredFields)
.filter(validateFields);
}
Insert cell
{
const validPassports = `pid:087499704 hgt:74in ecl:grn iyr:2012 eyr:2030 byr:1980
hcl:#623a2f

eyr:2029 ecl:blu cid:129 byr:1989
iyr:2014 pid:896056539 hcl:#a97842 hgt:165cm

hcl:#888785
hgt:164cm byr:2001 iyr:2015 cid:88
pid:545766238 ecl:hzl
eyr:2022

iyr:2010 hgt:158cm hcl:#b6652a ecl:blu byr:1944 eyr:2021 pid:093154719`;
return parseInput(validPassports)
.filter(validateRequiredFields)
.filter(validateFields);
}
Insert cell
// 186 is too high
parseInput(input)
.filter(validateRequiredFields)
.filter(validateFields).length
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more