From dfc08ff2c6580bbeb3951b223e0332546ba3b0d9 Mon Sep 17 00:00:00 2001 From: Greg Brown Date: Thu, 6 May 2021 19:40:59 +0100 Subject: Introduce lambda expressions. --- chomp-bench/src/arith/nibble.rs | 141 ++++++++++++++------------- chomp-bench/src/json/nibble.rs | 209 +++++++++++++++++++++++----------------- 2 files changed, 194 insertions(+), 156 deletions(-) (limited to 'chomp-bench/src') diff --git a/chomp-bench/src/arith/nibble.rs b/chomp-bench/src/arith/nibble.rs index 54d9223..9feab51 100644 --- a/chomp-bench/src/arith/nibble.rs +++ b/chomp-bench/src/arith/nibble.rs @@ -1,26 +1,32 @@ +use std::mem; + chomp_macro::nibble! { - let opt(x) = _ : None | x : Some; - let star(x) = [rec](opt(x.rec)); - let plus(x) = (x : First).(star(x) : Rest); + let opt some = _ : None | some; + let plus iter = !(/plus/ iter . (opt plus)); + let star iter = opt (plus iter); - let ws = star(" "); - let list(x, p) = (x : First).(star(p.ws.x) : Rest); + let ws = star " "; + let list inner p = !(/list/ inner . opt (p . ws . list)); - let number = plus("0" | "1" | "2"| "3" | "4" | "5" | "6" | "7" | "8" | "9"); - let term(e) = ((number : Pos | "-".ws.number : Neg | "(".ws.(e : Inner).")" : Parens) : RawTerm).ws; - let prod(e) = list(term(e), "*"|"/"); - let expr(e) = list(prod(e), "+"|"-"); - let arith = [e](expr(e)); + let digit = "0" | "1" | "2"| "3" | "4" | "5" | "6" | "7" | "8" | "9"; + let number = plus digit; + let term expr = + (( number : Pos + | "-" . ws . number : Neg + | "(" . ws . expr . ")" : Parens + ) : RawTerm) . ws; + let prod expr = list (term expr) ("*"|"/"); + let arith expr = list (prod expr) ("+"|"-"); - match [rec]((" ".rec : Base | arith) : Ast); + match !(/rec/ " ".rec | !arith); } impl From for i64 { fn from(mut a: Ast) -> Self { loop { - match a.0 { - Ast1::Base1(b) => a = *b.rec1, - Ast1::Arith1(a) => return a.into(), + match a { + Ast::Branch1(cat) => a = *cat.rec1, + Ast::Branch2(arith) => return arith.into(), } } } @@ -28,67 +34,28 @@ impl From for i64 { impl From for i64 { fn from(a: Arith1) -> Self { - a.0.into() - } -} - -impl From for i64 { - fn from(l: Expr1) -> Self { - let mut acc = l.prod1.into(); - let mut rest = l.rest1; - loop { - match rest.0 { - Opt5::None1(_) => return acc, - Opt5::Some1(s) => { - let v: i64 = s.x1.prod1.into(); - match s.x1.p1 { - P2::Branch1(_) => acc += v, - P2::Branch2(_) => acc -= v, - } - rest = *s.rec1; - }, + let acc = a.prod1.into(); + a.opt1.into_iter().fold(acc, |acc, (p, prod)| { + let v: i64 = prod.into(); + match p { + P2::Branch1(_) => acc + v, + P2::Branch2(_) => acc - v, } - } + }) } } impl From for i64 { - fn from(l: Prod1) -> Self { - let mut acc = l.term1.into(); - let mut rest = l.rest1; - loop { - match rest.0 { - Opt3::None1(_) => return acc, - Opt3::Some1(s) => { - let v: i64 = s.x1.term1.into(); - match s.x1.p1 { - P1::Branch1(_) => acc *= v, - P1::Branch2(_) => acc /= v, - } - rest = *s.rec1; - } + fn from(p: Prod1) -> Self { + let acc = p.term1.into(); + p.opt1.into_iter().fold(acc, |acc, (p, term)| { + let v: i64 = term.into(); + match p { + P1::Branch1(_) => acc * v, + P1::Branch2(_) => acc / v, } - } - } -} + }) -impl From for i64 { - fn from(l: Prod2) -> Self { - let mut acc = l.term1.into(); - let mut rest = l.rest1; - loop { - match rest.0 { - Opt4::None1(_) => return acc, - Opt4::Some1(s) => { - let v: i64 = s.x1.term1.into(); - match s.x1.p1 { - P1::Branch1(_) => acc *= v, - P1::Branch2(_) => acc /= v, - } - rest = *s.rec1; - } - } - } } } @@ -97,7 +64,7 @@ impl From for i64 { match t.raw_term1 { RawTerm1::Pos1(n) => n.into(), RawTerm1::Neg1(n) => -i64::from(n.number1), - RawTerm1::Parens1(p) => (*p.e1).into(), + RawTerm1::Parens1(p) => (*p.expr1).into(), } } } @@ -107,3 +74,39 @@ impl From for i64 { p.to_string().parse().unwrap() } } + +impl From for i64 { + fn from(p: Number1) -> Self { + p.to_string().parse().unwrap() + } +} + +impl Iterator for Opt5 { + type Item = (P2 , Prod1); + + fn next(&mut self) -> Option { + let orig = mem::replace(self, Self::None1(Epsilon)); + match orig { + Self::None1(_) => None, + Self::Some1(some) => { + *self = some.list1.opt1; + Some((some.p1, some.list1.prod1)) + } + } + } +} + +impl Iterator for Opt4 { + type Item = (P1 , Term1); + + fn next(&mut self) -> Option { + let orig = mem::replace(self, Self::None1(Epsilon)); + match orig { + Self::None1(_) => None, + Self::Some1(some) => { + *self = some.list1.opt1; + Some((some.p1, some.list1.term1)) + } + } + } +} diff --git a/chomp-bench/src/json/nibble.rs b/chomp-bench/src/json/nibble.rs index 9c0cdb7..a27ccff 100644 --- a/chomp-bench/src/json/nibble.rs +++ b/chomp-bench/src/json/nibble.rs @@ -1,25 +1,30 @@ use super::{decode_pair, Value}; -use std::{collections::HashMap, convert::TryInto, ops::RangeInclusive}; +use std::{collections::HashMap, convert::TryInto, mem, ops::RangeInclusive}; use chomp_macro::nibble; // Note: this is only an ASCII subset. Need to add character sets. nibble! { - let opt(x) = _ : None | x : Some; - let plus(x) = [rec](x . opt(rec)); - let star(x) = [rec](opt(x . rec)); - let sep(x, p) = [rec](x . opt(p . rec)); + let opt some = _ : None | some; + let plus iter = !(/rec/ iter . opt rec); + let star iter = !(/rec/ opt (iter . rec)); let ws_char = " " | "\t" | "\n" | "\r"; - let ws = star(ws_char); + let ws = star ws_char; + + let sep iter = !(/rec/ iter . opt ("," . ws . rec)); + let digit_1_9 = "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9"; - let digit = "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9"; + let digit = "0" | digit_1_9; - let unsigned_number = (("0" | digit_1_9 . star(digit)) : Int) - . (opt("." . plus(digit)) : Frac) - . (opt(("e" | "E") . opt("+" | "-") . plus(digit)) : Exp); - let number = unsigned_number : Positive | "-" . unsigned_number : Negative; + let unsigned_number = + (("0" | digit_1_9 . star digit) : Int) + . (opt ("." . plus digit) : Frac) + . (opt (("e" | "E") . opt ("+" | "-") . plus digit) : Exp); + let number = + unsigned_number : Positive + | "-" . unsigned_number : Negative; let hex = "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" | @@ -37,38 +42,39 @@ nibble! { "`" | "a" | "b" | "c" | "d" | "e" | "f" | "g" | "h" | "i" | "j" | "k" | "l" | "m" | "n" | "o" | "p" | "q" | "r" | "s" | "t" | "u" | "v" | "w" | - "x" | "y" | "z" | "{" | "|" | "}" | "~") : Literal | - "\\" . ( - ("\"" | "\\" | "/" | "b" | "f" | "n" | "r" | "t") : Ascii | - "u" . hex . hex . hex . hex : Unicode - ) : Escape; - - let string = "\"" . star(char) . "\""; - - let member(value) = (string : Key) . ws . ":" . ws . (value : Value) . ws; - let object(value) = "{" . ws . opt(sep(member(value), "," . ws)) . "}"; - - let array(value) = "[" . ws . opt(sep(value . ws, "," . ws)) . "]"; - - let value = [value]( - "true" : True | - "false" : False | - "null" : Null | - number : Number | - string : String | - object(value) : Object | - array(value) : Array + "x" | "y" | "z" | "{" | "|" | "}" | "~" + ) : Literal | + "\\" . ( + ("\"" | "\\" | "/" | "b" | "f" | "n" | "r" | "t") : Ascii | + "u" . hex . hex . hex . hex : Unicode + ) : Escape; + + let string = "\"" . star char . "\""; + + let member value = (string : Key) . ws . ":" . ws . value . ws; + let object value = "{" . ws . opt (sep (member value)) . "}"; + + let array value = "[" . ws . opt (sep (value . ws)) . "]"; + + let value = !(/value/ + "true" : True + | "false" : False + | "null" : Null + | number : Number + | string : String + | object value : Object + | array value : Array ); - match [rec](ws_char . rec | value . ws); + match !(/rec/ ws_char . rec | value . ws); } impl From for Value { fn from(mut ast: Ast) -> Self { loop { - match ast.0 { - Alt184::Branch1(cat) => ast = *cat.rec1, - Alt184::Branch2(cat) => return cat.value1.into(), + match ast { + Ast::Branch1(cat) => ast = *cat.rec1, + Ast::Branch2(cat) => return cat.value1.into(), } } } @@ -76,14 +82,14 @@ impl From for Value { impl From for Value { fn from(value: Value1) -> Self { - match value.0 { - Alt182::Null1(_) => Self::Null, - Alt182::True1(_) => Self::Bool(true), - Alt182::False1(_) => Self::Bool(false), - Alt182::Number1(n) => Self::Number(n.into()), - Alt182::String1(s) => Self::String(s.into()), - Alt182::Object1(o) => Self::Object(o.into()), - Alt182::Array1(a) => Self::Array(a.into()), + match value { + Value1::Null1(_) => Self::Null, + Value1::True1(_) => Self::Bool(true), + Value1::False1(_) => Self::Bool(false), + Value1::Number1(n) => Self::Number(n.into()), + Value1::String1(s) => Self::String(s.into()), + Value1::Object1(o) => Self::Object(o.into()), + Value1::Array1(a) => Self::Array(a.into()), } } } @@ -100,16 +106,16 @@ impl From for String { } } -impl Iterator for Star2 { +impl Iterator for Opt5 { type Item = char; fn next(&mut self) -> Option { - fn next(star: &mut Star2) -> Option { - match std::mem::replace(star, Star2(Opt5::None1(Epsilon))).0 { + fn next(star: &mut Opt5) -> Option { + match std::mem::replace(star, Opt5::None1(Epsilon)) { Opt5::None1(_) => None, - Opt5::Some1(s) => { - *star = *s.rec1; - Some(s.char1) + Opt5::Some1(some) => { + *star = *some.rec1; + Some(some.char1) } } } @@ -161,73 +167,102 @@ impl Iterator for Star2 { impl From for HashMap { fn from(object: Object1) -> Self { - match object.opt1 { - Opt8::None1(_) => HashMap::new(), - Opt8::Sep1(s) => s - .into_iter() - .map(|m| (m.key1.into(), (*m.value1).into())) - .collect(), - } + object + .opt1 + .into_iter() + .map(|m| (m.key1.into(), (*m.value1).into())) + .collect() } } -impl IntoIterator for Sep1 { +impl IntoIterator for Opt8 { type Item = Member1; - type IntoIter = Sep1Iter; + type IntoIter = Opt7; fn into_iter(self) -> Self::IntoIter { - Sep1Iter(Some(self)) + match self { + Self::None1(_) => Opt7::None1(Epsilon), + Self::Sep1(sep) => Opt7::Some1(Some8 { + part1: Lit75, + ws1: Ws1::None1(Epsilon), + rec1: Box::new(sep), + }), + } } } -pub struct Sep1Iter(Option); - -impl Iterator for Sep1Iter { +impl Iterator for Opt7 { type Item = Member1; fn next(&mut self) -> Option { - let inner = self.0.take()?.0; - let res = inner.member1; - self.0 = match inner.opt1 { + let orig = mem::replace(self, Self::None1(Epsilon)); + match orig { Opt7::None1(_) => None, - Opt7::Some1(s) => Some(*s.rec1), - }; - Some(res) + Opt7::Some1(some) => { + *self = some.rec1.opt1; + Some(some.rec1.member1) + } + } } } impl From for Vec { fn from(array: Array1) -> Self { - match array.opt1 { - Opt10::None1(_) => Vec::new(), - Opt10::Sep1(s) => s.into_iter().map(|x| (*x.value1).into()).collect(), - } + array.opt1.into_iter().map(Value::from).collect() } } -impl IntoIterator for Sep2 { - type Item = X1; +impl IntoIterator for Opt10 { + type Item = Value1; - type IntoIter = Sep2Iter; + type IntoIter = Opt9; fn into_iter(self) -> Self::IntoIter { - Sep2Iter(Some(self)) + match self { + Self::None1(_) => Opt9::None1(Epsilon), + Self::Sep1(sep) => Opt9::Some1(Some9 { part1: Lit75, ws1: Ws1::None1(Epsilon), rec1: Box::new(sep)}) + } } } -pub struct Sep2Iter(Option); - -impl Iterator for Sep2Iter { - type Item = X1; +impl Iterator for Opt9 { + type Item = Value1; fn next(&mut self) -> Option { - let inner = self.0.take()?.0; - let res = inner.x1; - self.0 = match inner.opt1 { + let orig = mem::replace(self, Self::None1(Epsilon)); + match orig { Opt9::None1(_) => None, - Opt9::Some1(s) => Some(*s.rec1), - }; - Some(res) + Opt9::Some1(some) => { + *self = some.rec1.opt1; + Some(*some.rec1.iter1.value1) + } + } } } + +// impl IntoIterator for Sep2 { +// type Item = X1; + +// type IntoIter = Sep2Iter; + +// fn into_iter(self) -> Self::IntoIter { +// Sep2Iter(Some(self)) +// } +// } + +// pub struct Sep2Iter(Option); + +// impl Iterator for Sep2Iter { +// type Item = X1; + +// fn next(&mut self) -> Option { +// let inner = self.0.take()?.0; +// let res = inner.x1; +// self.0 = match inner.opt1 { +// Opt9::None1(_) => None, +// Opt9::Some1(s) => Some(*s.rec1), +// }; +// Some(res) +// } +// } -- cgit v1.2.3