Pattern matching works now
This commit is contained in:
@@ -89,47 +89,57 @@ pub async fn gen_match_macro_lib() -> Vec<GenMember> {
|
||||
matcher,
|
||||
}),
|
||||
build_macro(None, ["match", "match_rule", "_row", "=>"])
|
||||
.rule(mactreev!("pattern::match" { "..$" rules 0 }), [async |[rules]| {
|
||||
exec(async move |mut h| {
|
||||
let rule_lines = h
|
||||
.exec::<TAtom<Tuple>>(call(sym_ref(sym!(macros::resolve; i())), [
|
||||
mactree!(macros::common::semi_list "push" rules.clone();).to_gen().await,
|
||||
]))
|
||||
.await?;
|
||||
let mut rule_atoms = Vec::<(TAtom<MatcherAtom>, Expr)>::new();
|
||||
for line_exprh in rule_lines.iter() {
|
||||
let line_mac = h
|
||||
.exec::<TAtom<MacTree>>(Expr::from_handle(ExprHandle::from_ticket(*line_exprh).await))
|
||||
.await?;
|
||||
let Tpl((matcher, body)) = h
|
||||
.exec(call(sym_ref(sym!(macros::resolve; i())), [
|
||||
mactree!(pattern::_row "push" own(&line_mac).await ;).to_gen().await,
|
||||
.rule(mactreev!("pattern::match" "...$" value 0 { "..$" rules 0 }), [
|
||||
async |[value, rules]| {
|
||||
exec(async move |mut h| {
|
||||
let rule_lines = h
|
||||
.exec::<TAtom<Tuple>>(call(sym_ref(sym!(macros::resolve; i())), [
|
||||
mactree!(macros::common::semi_list "push" rules.clone();).to_gen().await,
|
||||
]))
|
||||
.await?;
|
||||
rule_atoms.push((matcher, body));
|
||||
}
|
||||
let base_case = lambda(0, [bot(mk_errv(
|
||||
i().i("No branches match").await,
|
||||
"None of the pattern provided matches this value",
|
||||
[rules.pos()],
|
||||
))]);
|
||||
let match_expr = stream::iter(rule_atoms.into_iter().rev())
|
||||
.fold(base_case, async |tail, (mat, body)| {
|
||||
lambda(0, [call(sym_ref(sym!(pattern::match_one; i())), [
|
||||
mat.to_gen().await,
|
||||
arg(0),
|
||||
body.to_gen().await,
|
||||
call(tail, [arg(0)]),
|
||||
])])
|
||||
})
|
||||
.await;
|
||||
Ok(match_expr)
|
||||
})
|
||||
.await
|
||||
}])
|
||||
let mut rule_atoms = Vec::<(TAtom<MatcherAtom>, Expr)>::new();
|
||||
for line_exprh in rule_lines.iter() {
|
||||
let line_mac = h
|
||||
.exec::<TAtom<MacTree>>(Expr::from_handle(
|
||||
ExprHandle::from_ticket(*line_exprh).await,
|
||||
))
|
||||
.await?;
|
||||
let Tpl((matcher, body)) = h
|
||||
.exec(call(sym_ref(sym!(macros::resolve; i())), [
|
||||
mactree!(pattern::_row "push" own(&line_mac).await ;).to_gen().await,
|
||||
]))
|
||||
.await?;
|
||||
rule_atoms.push((matcher, body));
|
||||
}
|
||||
let base_case = lambda(0, [bot(mk_errv(
|
||||
i().i("No branches match").await,
|
||||
"None of the patterns matches this value",
|
||||
[rules.pos()],
|
||||
))]);
|
||||
let match_expr = stream::iter(rule_atoms.into_iter().rev())
|
||||
.fold(base_case, async |tail, (mat, body)| {
|
||||
lambda(0, [call(sym_ref(sym!(pattern::match_one; i())), [
|
||||
mat.to_gen().await,
|
||||
arg(0),
|
||||
body.to_gen().await,
|
||||
call(tail, [arg(0)]),
|
||||
])])
|
||||
})
|
||||
.await;
|
||||
Ok(call(match_expr, [resolve(value).await]))
|
||||
})
|
||||
.await
|
||||
},
|
||||
])
|
||||
.rule(mactreev!(pattern::match_rule (( "...$" pattern 0 ))), [async |[pattern]| {
|
||||
resolve(mactree!(pattern::match_rule "push" pattern; )).await
|
||||
}])
|
||||
.rule(mactreev!(pattern::match_rule ( macros::common::_ )), [async |[]| {
|
||||
Ok(MatcherAtom {
|
||||
keys: Vec::new(),
|
||||
matcher: lambda(0, [OrcOpt(Some(Tpl(()))).to_gen().await]).create().await,
|
||||
})
|
||||
}])
|
||||
.rule(mactreev!(pattern::_row ( "...$" pattern 0 pattern::=> "...$" value 1 )), [
|
||||
async |[pattern, mut value]| {
|
||||
exec(async move |mut h| -> OrcRes<Tpl<(TAtom<MatcherAtom>, GExpr)>> {
|
||||
|
||||
Reference in New Issue
Block a user