fix match bug
i hope so. put equality checking after variable checking when matching symbols
This commit is contained in:
parent
17463c839f
commit
c7354d3c56
1 changed files with 9 additions and 7 deletions
16
src/main.rs
16
src/main.rs
|
@ -506,12 +506,12 @@ type Matches<'src> = HashMap<Symbol, &'src Sexp>;
|
||||||
pub fn matches<'src>(vars: &[Symbol], lhs: &Sexp, expr: &'src Sexp) -> Option<Matches<'src>> {
|
pub fn matches<'src>(vars: &[Symbol], lhs: &Sexp, expr: &'src Sexp) -> Option<Matches<'src>> {
|
||||||
match (lhs, expr) {
|
match (lhs, expr) {
|
||||||
(Sexp::Atom(a), Sexp::Atom(b)) => {
|
(Sexp::Atom(a), Sexp::Atom(b)) => {
|
||||||
if a == b {
|
if vars.contains(a) {
|
||||||
Some(HashMap::with_capacity(0))
|
|
||||||
} else if vars.contains(a) {
|
|
||||||
let mut out = HashMap::with_capacity(1);
|
let mut out = HashMap::with_capacity(1);
|
||||||
out.insert(*a, expr);
|
out.insert(*a, expr);
|
||||||
Some(out)
|
Some(out)
|
||||||
|
} else if a == b {
|
||||||
|
Some(HashMap::with_capacity(0))
|
||||||
} else {
|
} else {
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
|
@ -527,7 +527,7 @@ pub fn matches<'src>(vars: &[Symbol], lhs: &Sexp, expr: &'src Sexp) -> Option<Ma
|
||||||
}
|
}
|
||||||
(Sexp::List(_), Sexp::Atom(_)) => None,
|
(Sexp::List(_), Sexp::Atom(_)) => None,
|
||||||
(Sexp::List(xs), Sexp::List(ys)) => {
|
(Sexp::List(xs), Sexp::List(ys)) => {
|
||||||
if xs == ys {
|
if xs.is_empty() && ys.is_empty() {
|
||||||
Some(HashMap::with_capacity(0))
|
Some(HashMap::with_capacity(0))
|
||||||
} else if xs.len() == ys.len() {
|
} else if xs.len() == ys.len() {
|
||||||
xs.iter()
|
xs.iter()
|
||||||
|
@ -535,7 +535,7 @@ pub fn matches<'src>(vars: &[Symbol], lhs: &Sexp, expr: &'src Sexp) -> Option<Ma
|
||||||
.map(|(lhs, expr)| matches(vars, lhs, expr))
|
.map(|(lhs, expr)| matches(vars, lhs, expr))
|
||||||
.reduce(|a, b| match (a, b) {
|
.reduce(|a, b| match (a, b) {
|
||||||
(None, _) | (_, None) => None,
|
(None, _) | (_, None) => None,
|
||||||
(Some(a), Some(b)) => merge_matches(vars, a, b),
|
(Some(a), Some(b)) => merge_matches(vars, &a, &b),
|
||||||
})
|
})
|
||||||
.unwrap_or(None)
|
.unwrap_or(None)
|
||||||
} else {
|
} else {
|
||||||
|
@ -545,10 +545,11 @@ pub fn matches<'src>(vars: &[Symbol], lhs: &Sexp, expr: &'src Sexp) -> Option<Ma
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[must_use]
|
||||||
pub fn merge_matches<'src>(
|
pub fn merge_matches<'src>(
|
||||||
vars: &[Symbol],
|
vars: &[Symbol],
|
||||||
a: Matches<'src>,
|
a: &Matches<'src>,
|
||||||
b: Matches<'src>,
|
b: &Matches<'src>,
|
||||||
) -> Option<Matches<'src>> {
|
) -> Option<Matches<'src>> {
|
||||||
let mut out = HashMap::with_capacity(vars.len());
|
let mut out = HashMap::with_capacity(vars.len());
|
||||||
|
|
||||||
|
@ -579,6 +580,7 @@ pub fn merge_matches<'src>(
|
||||||
// }
|
// }
|
||||||
// }
|
// }
|
||||||
|
|
||||||
|
#[must_use]
|
||||||
pub fn rw(rule: &Rule, sexp: &Sexp) -> Sexp {
|
pub fn rw(rule: &Rule, sexp: &Sexp) -> Sexp {
|
||||||
if rule.lhs() == rule.rhs() {
|
if rule.lhs() == rule.rhs() {
|
||||||
return sexp.clone();
|
return sexp.clone();
|
||||||
|
|
Loading…
Reference in a new issue