mirror of
https://github.com/HenkKalkwater/aoc-2020
synced 2024-11-22 11:05:18 +00:00
Add day 4 part 2
This commit is contained in:
parent
d32366790b
commit
2b14c8d6f6
122
source/day4.d
122
source/day4.d
|
@ -7,19 +7,41 @@ import std.traits;
|
||||||
|
|
||||||
import dayutil;
|
import dayutil;
|
||||||
|
|
||||||
|
bool inbetween(T)(T value, T min, T max) {
|
||||||
|
return min <= value && value <= max;
|
||||||
|
}
|
||||||
|
|
||||||
struct SerName { string name; };
|
struct SerName { string name; };
|
||||||
struct Passport {
|
struct Passport {
|
||||||
@SerName("byr") string birthYear = "";
|
@SerName("byr") short birthYear = -1;
|
||||||
@SerName("cid") string countryId = "";
|
@SerName("cid") string countryId = "";
|
||||||
@SerName("ecl") string eyeColour = "";
|
@SerName("ecl") string eyeColour = "";
|
||||||
@SerName("eyr") string expireYear = "";
|
@SerName("eyr") short expireYear = -1;
|
||||||
@SerName("hcl") string hairColour = "";
|
@SerName("hcl") string hairColour = "";
|
||||||
@SerName("hgt") string height = "";
|
@SerName("hgt") string height = "";
|
||||||
@SerName("iyr") string issueYear = "";
|
@SerName("iyr") short issueYear = -1;
|
||||||
@SerName("pid") string passwordId = "";
|
@SerName("pid") string passwordId = "";
|
||||||
|
|
||||||
|
|
||||||
bool isValid() {
|
bool isValid() {
|
||||||
return birthYear.length > 0 && issueYear.length > 0 && expireYear.length > 0
|
import std.ascii;
|
||||||
|
import std.conv;
|
||||||
|
return birthYear.inbetween!short(1920, 2002)
|
||||||
|
&& issueYear.inbetween!short(2010, 2020)
|
||||||
|
&& expireYear.inbetween!short(2020, 2030)
|
||||||
|
&& (height.endsWith("cm")
|
||||||
|
? to!int(height[0..$-2]).inbetween(150, 193)
|
||||||
|
: height.endsWith("in")
|
||||||
|
? to!int(height[0..$-2]).inbetween(59, 76)
|
||||||
|
: false)
|
||||||
|
&& hairColour.startsWith("#") && hairColour.length == 7
|
||||||
|
&& hairColour[1..6].all!(c => c <= 'f' && c >= '0' && (c <= '9' || c >= 'a'))
|
||||||
|
&& eyeColour.among("amb", "blu", "brn", "gry", "grn", "hzl", "oth")
|
||||||
|
&& passwordId.length == 9 && passwordId.all!isDigit;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool hasAllFields() {
|
||||||
|
return birthYear >= 0 && issueYear >= 0 && expireYear >= 0
|
||||||
&& height.length > 0 && hairColour.length > 0 && eyeColour.length > 0
|
&& height.length > 0 && hairColour.length > 0 && eyeColour.length > 0
|
||||||
&& eyeColour.length > 0 && passwordId.length > 0;
|
&& eyeColour.length > 0 && passwordId.length > 0;
|
||||||
}
|
}
|
||||||
|
@ -27,17 +49,86 @@ struct Passport {
|
||||||
void run(string[] args) {
|
void run(string[] args) {
|
||||||
auto lines = stdin.byLineCopy.array;
|
auto lines = stdin.byLineCopy.array;
|
||||||
size_t result = parts!size_t(args,
|
size_t result = parts!size_t(args,
|
||||||
() => part1(lines));
|
() => part1(lines),
|
||||||
|
() => part2(lines));
|
||||||
writeln(result);
|
writeln(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t part1(Range)(Range range) if (isInputRange!Range) {
|
size_t part1(Range)(Range range) if (isInputRange!Range) {
|
||||||
|
return range.tokenize()
|
||||||
|
.map!(x => x.deserialize!Passport)
|
||||||
|
.filter!(x => x.hasAllFields)
|
||||||
|
.count;
|
||||||
|
}
|
||||||
|
|
||||||
|
unittest {
|
||||||
|
import std.string;
|
||||||
|
string testdata = q"EOS
|
||||||
|
ecl:gry pid:860033327 eyr:2020 hcl:#fffffd
|
||||||
|
byr:1937 iyr:2017 cid:147 hgt:183cm
|
||||||
|
|
||||||
|
iyr:2013 ecl:amb cid:350 eyr:2023 pid:028048884
|
||||||
|
hcl:#cfa07d byr:1929
|
||||||
|
|
||||||
|
hcl:#ae17e1 iyr:2013
|
||||||
|
eyr:2024
|
||||||
|
ecl:brn pid:760753108 byr:1931
|
||||||
|
hgt:179cm
|
||||||
|
|
||||||
|
hcl:#cfa07d eyr:2025 pid:166559648
|
||||||
|
iyr:2011 ecl:brn hgt:59in
|
||||||
|
EOS";
|
||||||
|
assert(testdata
|
||||||
|
.lineSplitter.part1 == 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
size_t part2(Range)(Range range) if (isInputRange!Range) {
|
||||||
return range.tokenize()
|
return range.tokenize()
|
||||||
.map!(x => x.deserialize!Passport)
|
.map!(x => x.deserialize!Passport)
|
||||||
.filter!(x => x.isValid)
|
.filter!(x => x.isValid)
|
||||||
.count;
|
.count;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unittest {
|
||||||
|
import std.string;
|
||||||
|
string invalid = q"EOF
|
||||||
|
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
|
||||||
|
EOF";
|
||||||
|
|
||||||
|
assert(invalid.lineSplitter.part2 == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
unittest {
|
||||||
|
import std.string;
|
||||||
|
string invalid = q"EOF
|
||||||
|
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
|
||||||
|
EOF";
|
||||||
|
|
||||||
|
assert(invalid.lineSplitter.part2 == 4);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Deserializes a type from an array in the form of [[key, value], ...] where key an value are
|
* Deserializes a type from an array in the form of [[key, value], ...] where key an value are
|
||||||
* strings.
|
* strings.
|
||||||
|
@ -88,24 +179,3 @@ auto tokenize(Range)(Range range) if (isInputRange!Range) {
|
||||||
.sort!(((a,b) => a[0] < b[0])));
|
.sort!(((a,b) => a[0] < b[0])));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
unittest {
|
|
||||||
import std.string;
|
|
||||||
string testdata = q"EOS
|
|
||||||
ecl:gry pid:860033327 eyr:2020 hcl:#fffffd
|
|
||||||
byr:1937 iyr:2017 cid:147 hgt:183cm
|
|
||||||
|
|
||||||
iyr:2013 ecl:amb cid:350 eyr:2023 pid:028048884
|
|
||||||
hcl:#cfa07d byr:1929
|
|
||||||
|
|
||||||
hcl:#ae17e1 iyr:2013
|
|
||||||
eyr:2024
|
|
||||||
ecl:brn pid:760753108 byr:1931
|
|
||||||
hgt:179cm
|
|
||||||
|
|
||||||
hcl:#cfa07d eyr:2025 pid:166559648
|
|
||||||
iyr:2011 ecl:brn hgt:59in
|
|
||||||
EOS";
|
|
||||||
assert(testdata
|
|
||||||
.lineSplitter.part1 == 2);
|
|
||||||
}
|
|
||||||
|
|
Loading…
Reference in a new issue