Skip to content

Commit

Permalink
Add join_nested_quantifiers simplification
Browse files Browse the repository at this point in the history
  • Loading branch information
teiesti committed Aug 20, 2024
1 parent f3435a3 commit 1bd7dc7
Showing 1 changed file with 65 additions and 1 deletion.
66 changes: 65 additions & 1 deletion src/simplifying/fol/ht.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ fn simplify_formula(formula: Formula) -> Formula {
Box::new(remove_identities),
Box::new(remove_annihilations),
Box::new(remove_idempotences),
Box::new(join_nested_quantifiers),
])
}

Expand Down Expand Up @@ -111,9 +112,38 @@ fn remove_idempotences(formula: Formula) -> Formula {
}
}

fn join_nested_quantifiers(formula: Formula) -> Formula {
// Remove nested quantifiers
// e.g. q X ( q Y F(X,Y) ) => q X Y F(X,Y)

match formula.unbox() {
// forall X ( forall Y F(X,Y) ) => forall X Y F(X,Y)
// exists X ( exists Y F(X,Y) ) => exists X Y F(X,Y)
UnboxedFormula::QuantifiedFormula {
quantification: outer_quantification,
formula:
Formula::QuantifiedFormula {
quantification: mut inner_quantification,
formula: inner_formula,
},
} if outer_quantification.quantifier == inner_quantification.quantifier => {
let mut variables = outer_quantification.variables;
variables.append(&mut inner_quantification.variables);
variables.sort();
variables.dedup();

inner_formula.quantify(outer_quantification.quantifier, variables)
}
x => x.rebox(),
}
}

#[cfg(test)]
mod tests {
use super::simplify_formula;
use {
super::{join_nested_quantifiers, simplify_formula},
crate::{convenience::apply::Apply as _, syntax_tree::fol::Formula},
};

#[test]
fn test_simplify_formula() {
Expand All @@ -137,4 +167,38 @@ mod tests {
)
}
}

#[test]
fn test_join_nested_quantifiers() {
for (src, target) in [
("exists X (exists Y (X = Y))", "exists X Y (X = Y)"),
(
"exists X Y ( exists Z ( X < Y and Y < Z ))",
"exists X Y Z ( X < Y and Y < Z )",
),
(
"exists X (exists Y (X = Y and q(Y)))",
"exists X Y (X = Y and q(Y))",
),
(
"exists X (exists X$i (p(X) -> X$i < 1))",
"exists X X$i (p(X) -> X$i < 1)",
),
(
"forall X Y (forall Y Z (p(X,Y) and q(Y,Z)))",
"forall X Y Z (p(X,Y) and q(Y,Z))",
),
(
"forall X (forall Y (forall Z (X = Y = Z)))",
"forall X Y Z (X = Y = Z)",
),
] {
assert_eq!(
src.parse::<Formula>()
.unwrap()
.apply(&mut join_nested_quantifiers),
target.parse().unwrap()
)
}
}
}

0 comments on commit 1bd7dc7

Please sign in to comment.