From 67e190d766c677cc761166f5c1a9a19e00dfc0b4 Mon Sep 17 00:00:00 2001 From: Vitaly Bogdanov Date: Tue, 17 Sep 2024 12:27:45 +0300 Subject: [PATCH] Return NotReducible when results are empty because of variable loops --- lib/src/metta/interpreter_minimal.rs | 67 +++++++++++++++------------- 1 file changed, 35 insertions(+), 32 deletions(-) diff --git a/lib/src/metta/interpreter_minimal.rs b/lib/src/metta/interpreter_minimal.rs index 37a973cbc..7835cf790 100644 --- a/lib/src/metta/interpreter_minimal.rs +++ b/lib/src/metta/interpreter_minimal.rs @@ -542,27 +542,28 @@ fn query<'a, T: Space>(space: T, prev: Option>>, to_eval: Atom let var_x = &VariableAtom::new("X").make_unique(); let query = Atom::expr([EQUAL_SYMBOL, to_eval.clone(), Atom::Variable(var_x.clone())]); let results = space.query(&query); + log::debug!("interpreter_minimal::query: query: {}", query); + log::debug!("interpreter_minimal::query: results.len(): {}, bindings.len(): {}, results: {} bindings: {}", + results.len(), bindings.len(), results, bindings); + let call_stack = call_to_stack(to_eval, vars, prev.clone()); + let result = |res, bindings| eval_result(prev.clone(), res, &call_stack, bindings); + let results: Vec = results.into_iter().flat_map(|b| { + log::debug!("interpreter_minimal::query: b: {}", b); + b.merge_v2(&bindings).into_iter() + }).filter_map(move |b| { + b.resolve(&var_x).map_or(None, |res| { + if b.has_loops() { + None + } else { + Some(result(res, b)) + } + }) + }) + .collect(); if results.is_empty() { finished_result(return_not_reducible(), bindings, prev) } else { - log::debug!("interpreter_minimal::query: query: {}", query); - log::debug!("interpreter_minimal::query: results.len(): {}, bindings.len(): {}, results: {} bindings: {}", - results.len(), bindings.len(), results, bindings); - let call_stack = call_to_stack(to_eval, vars, prev.clone()); - let result = |res, bindings| eval_result(prev.clone(), res, &call_stack, bindings); - results.into_iter().flat_map(|b| { - log::debug!("interpreter_minimal::query: b: {}", b); - b.merge_v2(&bindings).into_iter() - }).filter_map(move |b| { - b.resolve(&var_x).map_or(None, |res| { - if b.has_loops() { - None - } else { - Some(result(res, b)) - } - }) - }) - .collect() + results } } @@ -730,23 +731,25 @@ fn unify(stack: Stack, bindings: Bindings) -> Vec { }; let matches: Vec = match_atoms(&atom, &pattern).collect(); + let result = |bindings| { + let stack = Stack::finished(prev.clone(), then.clone()); + InterpretedAtom(stack, bindings) + }; + let bindings_ref = &bindings; + let matches: Vec = matches.into_iter().flat_map(move |b| { + b.merge_v2(bindings_ref).into_iter().filter_map(move |b| { + if b.has_loops() { + None + } else { + Some(result(b)) + } + }) + }) + .collect(); if matches.is_empty() { finished_result(else_, bindings, prev) } else { - let result = |bindings| { - let stack = Stack::finished(prev.clone(), then.clone()); - InterpretedAtom(stack, bindings) - }; - matches.into_iter().flat_map(move |b| { - b.merge_v2(&bindings).into_iter().filter_map(move |b| { - if b.has_loops() { - None - } else { - Some(result(b)) - } - }) - }) - .collect() + matches } }