1
0
mirror of https://github.com/ellmau/adf-obdd.git synced 2025-12-19 09:29:36 +01:00

BUGFIX three valued interpretations and complete interpretations (#16)

A couple of bugs have been identified, where the complete interpretation either identified too many interpretations as being complete (bug in complete_iter) or too less interpretations (bug in ThreeValuedInterpretationsIterator)

They are fixed now
This commit is contained in:
Stefan Ellmauthaler 2022-01-13 13:16:49 +01:00 committed by GitHub
parent f0f9789bc8
commit 864419d033
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 124 additions and 57 deletions

2
Cargo.lock generated
View File

@ -4,7 +4,7 @@ version = 3
[[package]] [[package]]
name = "adf_bdd" name = "adf_bdd"
version = "0.1.3" version = "0.1.4"
dependencies = [ dependencies = [
"assert_cmd", "assert_cmd",
"assert_fs", "assert_fs",

View File

@ -234,20 +234,20 @@ impl Adf {
'a: 'c, 'a: 'c,
'b: 'c, 'b: 'c,
{ {
ThreeValuedInterpretationsIterator::new(grounded).filter(|interpretation| { let ac = self.ac.clone();
interpretation.iter().all(|ac| { ThreeValuedInterpretationsIterator::new(grounded).filter(move |interpretation| {
ac.compare_inf( interpretation.iter().enumerate().all(|(ac_idx, it)| {
&interpretation log::trace!("idx [{}], term: {}", ac_idx, it);
.iter() it.compare_inf(&interpretation.iter().enumerate().fold(
.enumerate() ac[ac_idx],
.fold(*ac, |acc, (var, term)| { |acc, (var, term)| {
if term.is_truth_value() { if term.is_truth_value() {
self.bdd.restrict(acc, Var(var), term.is_true()) self.bdd.restrict(acc, Var(var), term.is_true())
} else { } else {
acc acc
} }
}), },
) ))
}) })
}) })
} }
@ -421,21 +421,30 @@ mod test {
assert_eq!( assert_eq!(
adf.complete(0), adf.complete(0),
vec![ [
vec![Term(1), Term(3), Term(3), Term(9), Term(0), Term(1)], [Term(1), Term(3), Term(3), Term(9), Term(0), Term(1)],
vec![Term(1), Term(3), Term(3), Term(1), Term(0), Term(1)], [Term(1), Term(1), Term(1), Term(0), Term(0), Term(1)],
vec![Term(1), Term(3), Term(3), Term(0), Term(0), Term(1)], [Term(1), Term(0), Term(0), Term(1), Term(0), Term(1)]
vec![Term(1), Term(3), Term(1), Term(9), Term(0), Term(1)],
vec![Term(1), Term(3), Term(1), Term(1), Term(0), Term(1)],
vec![Term(1), Term(3), Term(1), Term(0), Term(0), Term(1)],
vec![Term(1), Term(3), Term(0), Term(0), Term(0), Term(1)],
vec![Term(1), Term(1), Term(1), Term(1), Term(0), Term(1)],
vec![Term(1), Term(1), Term(1), Term(0), Term(0), Term(1)],
vec![Term(1), Term(1), Term(0), Term(0), Term(0), Term(1)],
vec![Term(1), Term(0), Term(0), Term(0), Term(0), Term(1)],
vec![Term(1), Term(0), Term(1), Term(1), Term(0), Term(1)],
vec![Term(1), Term(0), Term(1), Term(0), Term(0), Term(1)]
] ]
); );
} }
#[test]
fn complete2() {
let parser = AdfParser::default();
parser.parse()("s(a).s(b).s(c).s(d).ac(a,c(v)).ac(b,b).ac(c,and(a,b)).ac(d,neg(b)).")
.unwrap();
let mut adf = Adf::from_parser(&parser);
assert_eq!(
adf.complete(0),
[
[Term(1), Term(3), Term(3), Term(7)],
[Term(1), Term(1), Term(1), Term(0)],
[Term(1), Term(0), Term(0), Term(1)]
]
);
for model in adf.complete(0) {
println!("{}", adf.print_interpretation(&model));
}
}
} }

View File

@ -176,29 +176,51 @@ impl ThreeValuedInterpretationsIterator {
fn decrement(&mut self) { fn decrement(&mut self) {
if let Some(ref mut current) = self.current { if let Some(ref mut current) = self.current {
if let Some((pos, val)) = current.iter().enumerate().find(|(idx, val)| **val > 0) { if !ThreeValuedInterpretationsIterator::decrement_vec(current) {
if pos > 0 && *val == 2 {
for elem in &mut current[0..pos] {
*elem = 2;
}
}
current[pos] -= 1;
if self.last_iteration {
if current.iter().all(|val| *val == 0) {
self.current = None; self.current = None;
} }
// if let Some((pos, val)) = current.iter().enumerate().find(|(idx, val)| **val > 0) {
// if pos > 0 && *val == 2 {
// for elem in &mut current[0..pos] {
// *elem = 2;
// }
// }
// current[pos] -= 1;
// if self.last_iteration {
// if current.iter().all(|val| *val == 0) {
// self.current = None;
// }
// }
// } else if !self.last_iteration {
// let len = current.len();
// if len <= 1 {
// self.current = None;
// } else {
// for elem in &mut current[0..len - 1] {
// *elem = 2;
// }
// }
// self.last_iteration = true;
//}
} }
} else if !self.last_iteration { }
let len = current.len();
if len <= 1 { fn decrement_vec(vector: &mut Vec<usize>) -> bool {
self.current = None; let mut cur_pos = None;
for (idx, value) in vector.iter_mut().enumerate() {
if *value > 0 {
*value -= 1;
cur_pos = Some(idx);
break;
}
}
if let Some(cur) = cur_pos {
for value in vector[0..cur].iter_mut() {
*value = 2;
}
true
} else { } else {
for elem in &mut current[0..len - 1] { false
*elem = 2;
}
}
self.last_iteration = true;
}
} }
} }
} }
@ -299,10 +321,6 @@ mod test {
iter.next(), iter.next(),
Some(vec![Term::TOP, Term::TOP, Term::BOT, Term::BOT, Term::TOP]) Some(vec![Term::TOP, Term::TOP, Term::BOT, Term::BOT, Term::TOP])
); );
assert_eq!(
iter.next(),
Some(vec![Term::TOP, Term::BOT, Term::BOT, Term::BOT, Term::TOP])
);
assert_eq!( assert_eq!(
iter.next(), iter.next(),
Some(vec![Term::TOP, Term::BOT, Term::BOT, Term(12), Term::TOP]) Some(vec![Term::TOP, Term::BOT, Term::BOT, Term(12), Term::TOP])
@ -311,7 +329,47 @@ mod test {
iter.next(), iter.next(),
Some(vec![Term::TOP, Term::BOT, Term::BOT, Term::TOP, Term::TOP]) Some(vec![Term::TOP, Term::BOT, Term::BOT, Term::TOP, Term::TOP])
); );
assert_eq!(
iter.next(),
Some(vec![Term::TOP, Term::BOT, Term::BOT, Term::BOT, Term::TOP])
);
assert_eq!(iter.next(), None); assert_eq!(iter.next(), None);
let testinterpretation = vec![Term(1), Term(3), Term(3), Term(7)];
let mut iter: Vec<Vec<Term>> =
ThreeValuedInterpretationsIterator::new(&testinterpretation).collect();
assert_eq!(
iter,
[
[Term(1), Term(3), Term(3), Term(7)],
[Term(1), Term(3), Term(3), Term(1)],
[Term(1), Term(3), Term(3), Term(0)],
[Term(1), Term(3), Term(1), Term(7)],
[Term(1), Term(3), Term(1), Term(1)],
[Term(1), Term(3), Term(1), Term(0)],
[Term(1), Term(3), Term(0), Term(7)],
[Term(1), Term(3), Term(0), Term(1)],
[Term(1), Term(3), Term(0), Term(0)],
[Term(1), Term(1), Term(3), Term(7)],
[Term(1), Term(1), Term(3), Term(1)],
[Term(1), Term(1), Term(3), Term(0)],
[Term(1), Term(1), Term(1), Term(7)],
[Term(1), Term(1), Term(1), Term(1)],
[Term(1), Term(1), Term(1), Term(0)],
[Term(1), Term(1), Term(0), Term(7)],
[Term(1), Term(1), Term(0), Term(1)],
[Term(1), Term(1), Term(0), Term(0)],
[Term(1), Term(0), Term(3), Term(7)],
[Term(1), Term(0), Term(3), Term(1)],
[Term(1), Term(0), Term(3), Term(0)],
[Term(1), Term(0), Term(1), Term(7)],
[Term(1), Term(0), Term(1), Term(1)],
[Term(1), Term(0), Term(1), Term(0)],
[Term(1), Term(0), Term(0), Term(7)],
[Term(1), Term(0), Term(0), Term(1)],
[Term(1), Term(0), Term(0), Term(0)]
]
);
} }
#[test] #[test]
@ -330,12 +388,12 @@ mod test {
iter.decrement(); iter.decrement();
assert_eq!(iter.current, Some(vec![0, 1])); assert_eq!(iter.current, Some(vec![0, 1]));
iter.decrement(); iter.decrement();
assert_eq!(iter.current, Some(vec![0, 0]));
iter.decrement();
assert_eq!(iter.current, Some(vec![2, 0])); assert_eq!(iter.current, Some(vec![2, 0]));
iter.decrement(); iter.decrement();
assert_eq!(iter.current, Some(vec![1, 0])); assert_eq!(iter.current, Some(vec![1, 0]));
iter.decrement(); iter.decrement();
assert_eq!(iter.current, Some(vec![0, 0]));
iter.decrement();
assert_eq!(iter.current, None); assert_eq!(iter.current, None);
let testinterpretation = vec![Term::TOP, Term(22), Term::BOT, Term::TOP, Term::TOP]; let testinterpretation = vec![Term::TOP, Term(22), Term::BOT, Term::TOP, Term::TOP];