aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJan Krňávek <Jan.Krnavek@gmail.com>2024-03-10 22:48:35 +0100
committerJan Krňávek <Jan.Krnavek@gmail.com>2024-03-10 22:48:35 +0100
commit4a4bec6384f4ebabb33c70fd43f40b3894ce1bad (patch)
tree0cfd931021cbed14fbe79f0dbab9b36d490d1065
parenteb5bf748cf07c8bb20e1e41dfcce3478b9c54dde (diff)
downloadperlweeklychallenge-club-4a4bec6384f4ebabb33c70fd43f40b3894ce1bad.tar.gz
perlweeklychallenge-club-4a4bec6384f4ebabb33c70fd43f40b3894ce1bad.tar.bz2
perlweeklychallenge-club-4a4bec6384f4ebabb33c70fd43f40b3894ce1bad.zip
solutions week 259
-rw-r--r--challenge-259/wambash/raku/ch-1.raku20
-rw-r--r--challenge-259/wambash/raku/ch-2.raku72
2 files changed, 92 insertions, 0 deletions
diff --git a/challenge-259/wambash/raku/ch-1.raku b/challenge-259/wambash/raku/ch-1.raku
new file mode 100644
index 0000000000..8daddb66b0
--- /dev/null
+++ b/challenge-259/wambash/raku/ch-1.raku
@@ -0,0 +1,20 @@
+#!/usr/bin/env raku
+
+sub banking-day-offset (Date() $start-day,+bank-holidays,:$offset) {
+ $start-day, *.later(:1day) ... *
+ andthen .grep: *.day-of-week != 6|7
+ andthen .grep: { $_ ∉ bank-holidays }\
+ andthen .skip: $offset
+ andthen .head
+}
+
+multi MAIN (Bool :test($)!) {
+ use Test;
+ is banking-day-offset('2018-06-28'.Date, <2018-07-03>».Date):3offset, '2018-07-04'.Date;
+ is banking-day-offset('2018-06-28'.Date, ):3offset, '2018-07-03'.Date;
+ done-testing;
+}
+
+multi MAIN ($start-day,+bank-holidays,:$offset) {
+ say banking-day-offset $start-day, bank-holidays».Date,:$offset
+}
diff --git a/challenge-259/wambash/raku/ch-2.raku b/challenge-259/wambash/raku/ch-2.raku
new file mode 100644
index 0000000000..42b4d64930
--- /dev/null
+++ b/challenge-259/wambash/raku/ch-2.raku
@@ -0,0 +1,72 @@
+#!/usr/bin/env raku
+
+grammar LineParser {
+ rule TOP { <.ws> <tag>[ <lines> {} <endtag($<tag><id>)>]? }
+
+ rule tag { '{%' ~ '%}' [ <id> <field> *] }
+
+ token id { \w+ }
+ rule field { <name> '=' <value> }
+ token name { \w+ }
+ token value { \d+ | '"' ~ '"' <value-string> } #"
+ token value-string { [<-["]> | '\"' | '\\']* }
+
+ token lines { [<!before '{%'>.]* }
+ rule endtag($id) { '{%' ~ '%}' ['end'$id] }
+}
+
+class LineAction {
+ method TOP ($/) { make %(|$<tag>.made, |$<lines>.made ) }
+ method tag ($/) { make %( name => ~$<id>, fields => %( $<field>».made ) ) }
+ method field ($/) { make ~$<name> => $<value>.made }
+ method value ($/) { make $<value-string>.made // +$/ }
+ method value-string ($/) { make ~$/ }
+ method lines ($/) { make (text => ~$/.trim) }
+}
+
+sub line-parser ($string) {
+ LineParser.parse( $string, actions => LineAction.new)
+ andthen .made
+}
+
+multi MAIN (Bool :test($)!) {
+ use Test;
+
+ is LineParser.parse( 'field1 = "value1"', :rule<field>).<name>, 'field1';
+ is LineParser.parse( 'field1="value1"', :rule<field>).<value><value-string>, 'value1';
+ is LineParser.parse( 'field1 = 12', :rule<field>).<value>, 12;
+ is LineParser.parse('\"quoted\"', :rule<value-string> ), '\"quoted\"';
+ is LineParser.parse('Title \"quoted\" done', :rule<value-string> ).so, True;
+ is LineParser.parse('abab {a', :rule<lines> ).so, True;
+ is LineParser.parse('abab {%', :rule<lines> ).so, False;
+ is LineParser.parse('{% endid %}',:rule<endtag>,:args('id',) ).so, True;
+ is LineParser.parse('{% id %} Text {% endid %}', ).<lines>, 'Text ';
+ is LineParser.parse('{% tag %} Text {% endtag %}', ).<tag><id>, 'tag';
+ is LineParser.parse('{% id field1="value1" field2="value2" field3=42 %}')<tag><field>»<name>,
+ <field1 field2 field3>;
+ is LineParser.parse('{% youtube title="Title \"quoted\" done" %}')<tag><id>, 'youtube';
+
+ is-deeply LineParser.parse( 'field1 = "value1"', :rule<field>, actions => LineAction.new).made, (field1 => 'value1');
+ is-deeply LineParser.parse( 'field1 = 12', :rule<field>, actions => LineAction.new).made, (field1 => 12);
+
+ my %parsed := %(
+ name => 'id',
+ fields => {
+ field1 => 'value1',
+ field2 => 'value2',
+ field3 => 42,
+ },
+ text => 'LINES'
+ );
+ is-deeply line-parser('{% id t=1 tit="a" %} Text {% endid %}'), %(:fields(%(:t(1), :tit("a"))), :name("id"), :text("Text"));
+ is-deeply line-parser('
+ {% id field1="value1" field2="value2" field3=42 %}
+ LINES
+ {% endid %}
+ '), %parsed;
+ done-testing;
+}
+
+multi MAIN ($string) {
+ say line-parser $string
+}