|
|
|
|
Quelle Rewriting.thy
Sprache: Isabelle
|
|
(*
Author: Salomon Sickert
Author: Benedikt Seidl
Author: Alexander Schimpf (original entry: CAVA/LTL_Rewrite.thy)
License: BSD
*)
section ‹Rewrite Rules for LTL Simplification›
theory Rewriting
imports
LTL "HOL-Library.Extended_Nat"
begin
text ‹This theory provides rewrite rules for the simplification of LTL formulas. It supports:
\begin{itemize}
\item Constants Removal
\item @{const Next_ltln}-Normalisation
\item Modal Simplification (based on pure eventual, pure universal, or suspendable formulas)
\item Syntactic Implication Checking
\end{itemize}
It reuses parts of LTL\_Rewrite.thy (CAVA, LTL\_TO\_GBA). Furthermore, some rules were taken from
cite‹"DBLP:conf/cav/SomenziB00"› and cite‹"DBLP:conf/tacas/BabiakKRS12"›. All functions are defined for @{type ltln}.›
subsection ‹Constant Eliminating Constructors›
definition mk_and
where
"mk_and x y ≡ case x of falsen → falsen | truen → y | _ → (case y of falsen → falsen | truen → x | _ → x andn y)"
definition mk_or
where
"mk_or x y ≡ case x of falsen → y | truen → truen | _ → (case y of truen → truen | falsen → x | _ → x orn y)"
fun remove_strong_ops
where
"remove_strong_ops (x Un y) = remove_strong_ops y"
| "remove_strong_ops (x Mn y) = x andn y"
| "remove_strong_ops (x orn y) = remove_strong_ops x orn remove_strong_ops y"
| "remove_strong_ops x = x"
fun remove_weak_ops
where
"remove_weak_ops (x Rn y) = remove_weak_ops y"
| "remove_weak_ops (x Wn y) = x orn y"
| "remove_weak_ops (x andn y) = remove_weak_ops x andn remove_weak_ops y"
| "remove_weak_ops x = x"
definition mk_finally
where
"mk_finally x ≡ case x of truen → truen | falsen → falsen | _ → Fn (remove_strong_ops x)"
definition mk_globally
where
"mk_globally x ≡ case x of truen → truen | falsen → falsen | _ → Gn (remove_weak_ops x)"
definition mk_until
where
"mk_until x y ≡ case x of falsen → y
| truen → mk_finally y
| _ → (case y of truen → truen | falsen → falsen | _ → x Un y)"
definition mk_release
where
"mk_release x y ≡ case x of truen → y
| falsen → mk_globally y
| _ → (case y of truen → truen | falsen → falsen | _ → x Rn y)"
definition mk_weak_until
where
"mk_weak_until x y ≡ case y of truen → truen
| falsen → mk_globally x
| _ → (case x of truen → truen | falsen → y | _ → x Wn y)"
definition mk_strong_release
where
"mk_strong_release x y ≡ case y of falsen → falsen
| truen → mk_finally x
| _ → (case x of truen → y | falsen → falsen | _ → x Mn y)"
definition mk_next
where
"mk_next x ≡ case x of truen → truen | falsen → falsen | _ → Xn x"
definition mk_next_pow (‹Xn''›)
where
"mk_next_pow n x ≡ case x of truen → truen | falsen → falsen | _ → (Next_ltln ^^ n) x"
lemma mk_and_semantics [simp]:
"w ⊨n mk_and x y ⟷ w ⊨n x andn y"
unfolding mk_and_def by (cases x; cases y; simp)
lemma mk_or_semantics [simp]:
"w ⊨n mk_or x y ⟷ w ⊨n x orn y"
unfolding mk_or_def by (cases x; cases y; simp)
lemma remove_strong_ops_sound [simp]:
"w ⊨n Fn (remove_strong_ops y) ⟷ w ⊨n Fn y"
by (induction y arbitrary: w) (auto; force)+
lemma remove_weak_ops_sound [simp]:
"w ⊨n Gn (remove_weak_ops y) ⟷ w ⊨n Gn y"
by (induction y arbitrary: w) (auto; force)+
lemma mk_finally_semantics [simp]:
"w ⊨n mk_finally x ⟷ w ⊨n Fn x"
by (simp add: mk_finally_def del: semantics_ltln.simps(8,9) remove_strong_ops.simps split: ltln.splits)
lemma mk_globally_semantics [simp]:
"w ⊨n mk_globally x ⟷ w ⊨n Gn x"
by (simp add: mk_globally_def del: semantics_ltln.simps(8,9) remove_weak_ops.simps split: ltln.splits)
lemma mk_until_semantics [simp]:
"w ⊨n mk_until x y ⟷ w ⊨n x Un y"
proof (cases x)
case (True_ltln)
show ?thesis
unfolding True_ltln mk_until_def
by (cases y) auto
next
case (False_ltln)
thus ?thesis
by (force simp: mk_until_def)
qed (cases y; force simp: mk_until_def)+
lemma mk_release_semantics [simp]:
"w ⊨n mk_release x y ⟷ w ⊨n x Rn y"
proof (cases x)
case (False_ltln)
thus ?thesis
unfolding False_ltln mk_release_def
by (cases y) auto
next
case (True_ltln)
thus ?thesis
by (force simp: mk_release_def)
qed (cases y; force simp: mk_release_def)+
lemma mk_weak_until_semantics [simp]:
"w ⊨n mk_weak_until x y ⟷ w ⊨n x Wn y"
proof (cases y)
case (False_ltln)
thus ?thesis
unfolding False_ltln mk_weak_until_def
by (cases x) auto
next
case (True_ltln)
thus ?thesis
by (force simp: mk_weak_until_def)
qed (cases x; force simp: mk_weak_until_def)+
lemma mk_strong_release_semantics [simp]:
"w ⊨n mk_strong_release x y ⟷ w ⊨n x Mn y"
proof (cases y)
case (True_ltln)
show ?thesis
unfolding True_ltln mk_strong_release_def
by (cases x) auto
next
case (False_ltln)
thus ?thesis
by (force simp: mk_strong_release_def)
qed (cases x; force simp: mk_strong_release_def)+
lemma mk_next_semantics [simp]:
"w ⊨n mk_next x ⟷ w ⊨n Xn x"
unfolding mk_next_def by (cases x; auto)
lemma mk_next_pow_semantics [simp]:
"w ⊨n mk_next_pow i x ⟷ suffix i w ⊨n x"
by (induction i arbitrary: w; cases x)
(auto simp: mk_next_pow_def)
lemma mk_next_pow_simp [simp, code_unfold]:
"mk_next_pow 0 x = x"
"mk_next_pow 1 x = mk_next x"
by (cases x; simp add: mk_next_pow_def mk_next_def)+
subsection ‹Constant Propagation›
fun is_constant :: "'a ltln → bool"
where
"is_constant truen = True"
| "is_constant falsen = True"
| "is_constant _ = False"
lemma is_constant_constructorsI:
"is_constant x ==> is_constant y ==> is_constant (mk_and x y)"
"¬is_constant x ==> ¬is_constant y ==> ¬is_constant (mk_and x y)"
"is_constant x ==> is_constant y ==> is_constant (mk_or x y)"
"¬is_constant x ==> ¬is_constant y ==> ¬is_constant (mk_or x y)"
"is_constant x ==> is_constant (mk_finally x)"
"¬is_constant x ==> ¬is_constant (mk_finally x)"
"is_constant x ==> is_constant (mk_globally x)"
"¬is_constant x ==> ¬is_constant (mk_globally x)"
"is_constant x ==> is_constant (mk_until y x)"
"¬is_constant x ==> ¬is_constant (mk_until y x)"
"is_constant x ==> is_constant (mk_release y x)"
"¬is_constant x ==> ¬is_constant (mk_release y x)"
"is_constant x ==> is_constant y ==> is_constant (mk_weak_until x y)"
"¬is_constant x ==> ¬is_constant y ==> ¬is_constant (mk_weak_until x y)"
"is_constant x ==> is_constant y ==> is_constant (mk_strong_release x y)"
"¬is_constant x ==> ¬is_constant y ==> ¬is_constant (mk_strong_release x y)"
"is_constant x ==> is_constant (mk_next x)"
"¬is_constant x ==> ¬is_constant (mk_next x)"
"is_constant x ==> is_constant (mk_next_pow n x)"
by (cases x; cases y; simp add: mk_and_def mk_or_def mk_finally_def mk_globally_def mk_until_def mk_release_def mk_weak_until_def mk_strong_release_def mk_next_def mk_next_pow_def)+
lemma is_constant_constructors_simps:
"mk_next_pow n x = falsen ⟷ x = falsen"
"mk_next_pow n x = truen ⟷ x = truen"
"is_constant (mk_next_pow n x) ⟷ is_constant x"
by (induction n) (cases x; simp add: mk_next_pow_def)+
lemma is_constant_constructors_simps2:
"is_constant (mk_and x y) ⟷ (x = truen ∧ y = truen ∨ x = falsen ∨ y = falsen)"
"is_constant (mk_or x y) ⟷ (x = falsen ∧ y = falsen ∨ x = truen ∨ y = truen)"
"is_constant (mk_finally x) ⟷ is_constant x"
"is_constant (mk_globally x) ⟷ is_constant x"
"is_constant (mk_until y x) ⟷ is_constant x"
"is_constant (mk_release y x) ⟷ is_constant x"
"is_constant (mk_next x) ⟷ is_constant x"
by ((cases x; cases y; simp add: mk_and_def),
(cases x; cases y; simp add: mk_or_def),
(meson is_constant_constructorsI)+)
lemma is_constant_constructors_simps3:
"is_constant (mk_weak_until x y) ⟷ (x = falsen ∧ y = falsen ∨ x = truen ∨ y = truen)"
"is_constant (mk_strong_release x y) ⟷ (x = truen ∧ y = truen ∨ x = falsen ∨ y = falsen)"
by (cases x; cases y; simp add: mk_weak_until_def mk_strong_release_def is_constant_constructors_simps2)+
lemma is_constant_semantics:
"is_constant φ ==> ((∀w. w ⊨n φ) ∨ ¬(∃w. w ⊨n φ))"
by (cases φ) auto
lemma until_constant_simp:
"is_constant ψ ==> w ⊨n φ Un ψ ⟷ w ⊨n ψ"
by (cases ψ) auto
lemma release_constant_simp:
"is_constant ψ ==> w ⊨n φ Rn ψ ⟷ w ⊨n ψ"
by (cases ψ) auto
lemma mk_next_pow_dist:
"mk_next_pow (i + j) φ = mk_next_pow i (mk_next_pow j φ)"
by (cases j; simp) (cases φ; simp add: mk_next_pow_def funpow_add; simp add: funpow_swap1)
lemma mk_next_pow_until:
"suffix (min i j) w ⊨n (mk_next_pow (i - j) φ) Un (mk_next_pow (j - i) ψ) ⟷ w ⊨n (mk_next_pow i φ) Un (mk_next_pow j ψ)"
by (simp add: mk_next_pow_dist min_def add.commute)
lemma mk_next_pow_release:
"suffix (min i j) w ⊨n (mk_next_pow (i - j) φ) Rn (mk_next_pow (j - i) ψ) ⟷ w ⊨n (mk_next_pow i φ) Rn (mk_next_pow j ψ)"
by (simp add: mk_next_pow_dist min_def add.commute)
subsection ‹X-Normalisation›
text ‹The following rewrite functions pulls the X-operator up in the syntax tree. This preprocessing
step enables the removal of X-operators in front of suspendable formulas. Furthermore constants are
removed as far as possible.›
fun the_enat_0 :: "enat → nat"
where
"the_enat_0 i = i"
| "the_enat_0 ∞ = 0"
lemma the_enat_0_simp [simp]:
"the_enat_0 0 = 0"
"the_enat_0 1 = 1"
by (simp add: zero_enat_def one_enat_def)+
fun combine :: "('a ltln → 'a ltln → 'a ltln) → ('a ltln * enat) → ('a ltln * enat) → ('a ltln * enat)"
where
"combine binop (φ, i) (ψ, j) = (
let
χ = binop (mk_next_pow (the_enat_0 (i - j)) φ) (mk_next_pow (the_enat_0 (j - i)) ψ)
in
(χ, if is_constant χ then ∞ else min i j))"
lemma fst_combine:
"fst (combine binop (φ, i) (ψ, j)) = binop (mk_next_pow (the_enat_0 (i - j)) φ) (mk_next_pow (the_enat_0 (j - i)) ψ)"
unfolding combine.simps by (meson fstI)
abbreviation to_ltln :: "('a ltln * enat) → 'a ltln"
where
"to_ltln x ≡ mk_next_pow (the_enat_0 (snd x)) (fst x)"
fun rewrite_X_enat :: "'a ltln → ('a ltln * enat)"
where
"rewrite_X_enat truen = (truen, ∞)"
| "rewrite_X_enat falsen = (falsen, ∞)"
| "rewrite_X_enat propn(a) = (propn(a), 0)"
| "rewrite_X_enat npropn(a) = (npropn(a), 0)"
| "rewrite_X_enat (φ andn ψ) = combine mk_and (rewrite_X_enat φ) (rewrite_X_enat ψ)"
| "rewrite_X_enat (φ orn ψ) = combine mk_or (rewrite_X_enat φ) (rewrite_X_enat ψ)"
| "rewrite_X_enat (φ Un ψ) = combine mk_until (rewrite_X_enat φ) (rewrite_X_enat ψ)"
| "rewrite_X_enat (φ Rn ψ) = combine mk_release (rewrite_X_enat φ) (rewrite_X_enat ψ)"
| "rewrite_X_enat (φ Wn ψ) = combine mk_weak_until (rewrite_X_enat φ) (rewrite_X_enat ψ)"
| "rewrite_X_enat (φ Mn ψ) = combine mk_strong_release (rewrite_X_enat φ) (rewrite_X_enat ψ)"
| "rewrite_X_enat (Xn φ) = (λ(φ, n). (φ, eSuc n)) (rewrite_X_enat φ)"
definition
"rewrite_X φ = to_ltln (rewrite_X_enat φ)"
lemma combine_infinity_invariant:
assumes "i = ∞ ⟷ is_constant x"
assumes "j = ∞ ⟷ is_constant y"
shows "combine mk_and (x, i) (y, j) = (z, k) ==> (k = ∞ ⟷ is_constant z)"
and "combine mk_or (x, i) (y, j) = (z, k) ==> (k = ∞ ⟷ is_constant z)"
and "combine mk_until (x, i) (y, j) = (z, k) ==> (k = ∞ ⟷ is_constant z)"
and "combine mk_release (x, i) (y, j) = (z, k) ==> (k = ∞ ⟷ is_constant z)"
and "combine mk_weak_until (x, i) (y, j) = (z, k) ==> (k = ∞ ⟷ is_constant z)"
and "combine mk_strong_release (x, i) (y, j) = (z, k) ==> (k = ∞ ⟷ is_constant z)"
by (cases i; cases j; simp add: assms Let_def; force intro: is_constant_constructorsI)+
lemma combine_and_or_semantics:
assumes "i = ∞ ⟷ is_constant φ"
assumes "j = ∞ ⟷ is_constant ψ"
shows "w ⊨n to_ltln (combine mk_and (φ, i) (ψ, j)) ⟷ w ⊨n to_ltln (φ, i) andn to_ltln (ψ, j)"
and "w ⊨n to_ltln (combine mk_or (φ, i) (ψ, j)) ⟷ w ⊨n to_ltln (φ, i) orn to_ltln (ψ, j)"
by ((cases i; cases j; simp add: min_def is_constant_constructors_simps is_constant_constructors_simps2 assms),
(cases ψ; insert assms; auto),
(cases φ; insert assms; auto),
(blast elim!: is_constant.elims))+
lemma combine_until_release_semantics:
assumes "i = ∞ ⟷ is_constant φ"
assumes "j = ∞ ⟷ is_constant ψ"
shows "w ⊨n to_ltln (combine mk_until (φ, i) (ψ, j)) ⟷ w ⊨n to_ltln (φ, i) Un to_ltln (ψ, j)"
and "w ⊨n to_ltln (combine mk_release (φ, i) (ψ, j)) ⟷ w ⊨n to_ltln (φ, i) Rn to_ltln (ψ, j)"
by ((cases i; cases j; simp add: is_constant_constructors_simps is_constant_constructors_simps2
until_constant_simp release_constant_simp mk_next_pow_until mk_next_pow_release del: semantics_ltln.simps),
(blast dest: is_constant_semantics),
(cases ψ; simp add: assms),
(cases φ; insert assms; auto simp: add.commute))+
(* TODO this proof is a bit slow and could be optimized *)
lemma combine_weak_until_strong_release_semantics:
assumes "i = ∞ ⟷ is_constant φ"
assumes "j = ∞ ⟷ is_constant ψ"
shows "w ⊨n to_ltln (combine mk_weak_until (φ, i) (ψ, j)) ⟷ w ⊨n to_ltln (φ, i) Wn to_ltln (ψ, j)"
and "w ⊨n to_ltln (combine mk_strong_release (φ, i) (ψ, j)) ⟷ w ⊨n to_ltln (φ, i) Mn to_ltln (ψ, j)"
by ((cases i; cases j; simp add: min_def is_constant_constructors_simps is_constant_constructors_simps3 del: semantics_ltln.simps),
(cases φ; simp add: assms),
(cases ψ; insert assms; auto simp: add.commute))+
lemma rewrite_X_enat_infinity_invariant:
"snd (rewrite_X_enat φ) = ∞ ⟷ is_constant (fst (rewrite_X_enat φ))"
proof (induction φ)
case (And_ltln φ ψ)
thus ?case
by (simp add: combine_infinity_invariant[OF And_ltln(1,2), unfolded prod.collapse])
next
case (Or_ltln φ ψ)
thus ?case
by (simp add: combine_infinity_invariant[OF Or_ltln(1,2), unfolded prod.collapse])
next
case (Until_ltln φ ψ)
thus ?case
by (simp add: combine_infinity_invariant[OF Until_ltln(1,2), unfolded prod.collapse])
next
case (Release_ltln φ ψ)
thus ?case
by (simp add: combine_infinity_invariant[OF Release_ltln(1,2), unfolded prod.collapse])
next
case (WeakUntil_ltln φ ψ)
thus ?case
by (simp add: combine_infinity_invariant[OF WeakUntil_ltln(1,2), unfolded prod.collapse])
next
case (StrongRelease_ltln φ ψ)
thus ?case
by (simp add: combine_infinity_invariant[OF StrongRelease_ltln(1,2), unfolded prod.collapse])
next
case (Next_ltln φ)
thus ?case
by (simp add: split_def) (metis eSuc_infinity eSuc_inject)
qed auto
lemma rewrite_X_enat_correct:
"w ⊨n φ ⟷ w ⊨n to_ltln (rewrite_X_enat φ)"
proof (induction φ arbitrary: w)
case (And_ltln φ ψ)
thus ?case
using combine_and_or_semantics[OF rewrite_X_enat_infinity_invariant rewrite_X_enat_infinity_invariant] by fastforce
next
case (Or_ltln φ ψ)
thus ?case
using combine_and_or_semantics[OF rewrite_X_enat_infinity_invariant rewrite_X_enat_infinity_invariant] by fastforce
next
case (Until_ltln φ ψ)
thus ?case
unfolding rewrite_X_enat.simps combine_until_release_semantics[OF rewrite_X_enat_infinity_invariant rewrite_X_enat_infinity_invariant, unfolded prod.collapse] by fastforce
next
case (Release_ltln φ ψ)
thus ?case
unfolding rewrite_X_enat.simps combine_until_release_semantics[OF rewrite_X_enat_infinity_invariant rewrite_X_enat_infinity_invariant, unfolded prod.collapse] by fastforce
next
case (WeakUntil_ltln φ ψ)
thus ?case
unfolding rewrite_X_enat.simps combine_weak_until_strong_release_semantics[OF rewrite_X_enat_infinity_invariant rewrite_X_enat_infinity_invariant, unfolded prod.collapse] by fastforce
next
case (StrongRelease_ltln φ ψ)
thus ?case
unfolding rewrite_X_enat.simps combine_weak_until_strong_release_semantics[OF rewrite_X_enat_infinity_invariant rewrite_X_enat_infinity_invariant, unfolded prod.collapse] by fastforce
next
case (Next_ltln φ)
moreover
have " w ⊨n to_ltln (rewrite_X_enat (Xn φ)) ⟷ suffix 1 w ⊨n to_ltln (rewrite_X_enat φ)"
by (simp add: split_def; cases "snd (rewrite_X_enat φ) ≠ ∞")
(auto simp: eSuc_def, auto simp: rewrite_X_enat_infinity_invariant eSuc_def dest: is_constant_semantics)
ultimately
show ?case
using semantics_ltln.simps(7) by blast
qed auto
lemma rewrite_X_sound [simp]:
"w ⊨n rewrite_X φ ⟷ w ⊨n φ"
using rewrite_X_enat_correct unfolding rewrite_X_def Let_def by auto
subsection ‹Pure Eventual, Pure Universal, and Suspendable Formulas›
fun pure_eventual :: "'a ltln → bool"
where
"pure_eventual truen = True"
| "pure_eventual falsen = True"
| "pure_eventual (μ andn μ') = (pure_eventual μ ∧ pure_eventual μ')"
| "pure_eventual (μ orn μ') = (pure_eventual μ ∧ pure_eventual μ')"
| "pure_eventual (μ Un μ') = (μ = truen ∨ pure_eventual μ')"
| "pure_eventual (μ Rn μ') = (pure_eventual μ ∧ pure_eventual μ')"
| "pure_eventual (μ Wn μ') = (pure_eventual μ ∧ pure_eventual μ')"
| "pure_eventual (μ Mn μ') = (pure_eventual μ ∧ pure_eventual μ' ∨ μ' = truen)"
| "pure_eventual (Xn μ) = pure_eventual μ"
| "pure_eventual _ = False"
fun pure_universal :: "'a ltln → bool"
where
"pure_universal truen = True"
| "pure_universal falsen = True"
| "pure_universal (ν andn ν') = (pure_universal ν ∧ pure_universal ν')"
| "pure_universal (ν orn ν') = (pure_universal ν ∧ pure_universal ν')"
| "pure_universal (ν Un ν') = (pure_universal ν ∧ pure_universal ν')"
| "pure_universal (ν Rn ν') = (ν = falsen ∨ pure_universal ν')"
| "pure_universal (ν Wn ν') = (pure_universal ν ∧ pure_universal ν' ∨ ν' = falsen)"
| "pure_universal (ν Mn ν') = (pure_universal ν ∧ pure_universal ν')"
| "pure_universal (Xn ν) = pure_universal ν"
| "pure_universal _ = False"
fun suspendable :: "'a ltln → bool"
where
"suspendable truen = True"
| "suspendable falsen = True"
| "suspendable (ξ andn ξ') = (suspendable ξ ∧ suspendable ξ')"
| "suspendable (ξ orn ξ') = (suspendable ξ ∧ suspendable ξ')"
| "suspendable (φ Un ξ) = (φ = truen ∧ pure_universal ξ ∨ suspendable ξ)"
| "suspendable (φ Rn ξ) = (φ = falsen ∧ pure_eventual ξ ∨ suspendable ξ)"
| "suspendable (φ Wn ξ) = (suspendable φ ∧ suspendable ξ ∨ pure_eventual φ ∧ ξ = falsen)"
| "suspendable (φ Mn ξ) = (suspendable φ ∧ suspendable ξ ∨ pure_universal φ ∧ ξ = truen)"
| "suspendable (Xn ξ) = suspendable ξ"
| "suspendable _ = False"
lemma pure_eventual_left_append:
"pure_eventual μ ==> w ⊨n μ ==> (u ⌢ w) ⊨n μ"
proof (induction μ arbitrary: u w)
case (Until_ltln μ μ')
moreover
then obtain i where "suffix i w ⊨n μ'"
by auto
hence "μ = truen ==> ?case"
by simp (metis suffix_conc_length suffix_suffix)
moreover
have "pure_eventual μ' ==> (u ⌢ w) ⊨n μ'"
by (metis ‹suffix i w ⊨n μ'› Until_ltln(2) prefix_suffix)
hence "pure_eventual μ' ==> ?case"
by force
ultimately
show ?case
by fastforce
next
case (Release_ltln μ μ')
thus ?case
by (cases "∀i. suffix i w ⊨n μ'"; simp_all)
(metis linear suffix_conc_snd gr0I not_less0 prefix_suffix suffix_0)+
next
case (WeakUntil_ltln μ μ')
thus ?case
by (cases "∀i. suffix i w ⊨n μ'"; simp_all)
(metis zero_le le0 nat_le_linear prefix_suffix suffix_0 suffix_conc_length suffix_conc_snd suffix_subseq_join)+
next
case (StrongRelease_ltln μ μ')
moreover
then obtain i where "suffix i w ⊨n μ andn μ'"
by auto
hence "μ' = truen ==> ?case"
by simp (metis suffix_conc_length suffix_suffix)
moreover
have "pure_eventual μ ==> pure_eventual μ' ==> (u ⌢ w) ⊨n μ andn μ'"
by (metis ‹suffix i w ⊨n μ andn μ'› calculation(1) calculation(2) prefix_suffix semantics_ltln.simps(5))
hence "pure_eventual μ ==> pure_eventual μ' ==> ?case"
by force
ultimately
show ?case
by fastforce
qed (auto, metis diff_zero le_0_eq not_less_eq_eq suffix_conc_length suffix_conc_snd word_split)
lemma pure_universal_suffix_closed:
"pure_universal ν ==> (u ⌢ w) ⊨n ν ==> w ⊨n ν"
proof (induction ν arbitrary: u w)
case (Until_ltln ν ν')
hence "∃i. suffix i (u ⌢ w) ⊨n ν' ∧ (∀j<i. suffix j (u ⌢ w) ⊨n ν)"
using semantics_ltln.simps(8) by blast
thus ?case
by simp (metis Until_ltln(1-3) le_0_eq le_eq_less_or_eq le_less_linear prefix_suffix pure_universal.simps(5) suffix_conc_fst suffix_conc_snd)
next
case (Release_ltln ν ν')
moreover
hence "∀i. suffix i (u ⌢ w) ⊨n ν' ∨ (∃j<i. suffix j (u ⌢ w) ⊨n ν)"
by simp
ultimately
show ?case
by simp (metis semantics_ltln.simps(2) not_less0 prefix_suffix suffix_0 suffix_conc_length suffix_suffix)
next
case (WeakUntil_ltln ν ν')
moreover
hence "∀i. suffix i (u ⌢ w) ⊨n ν ∨ (∃j≤i. suffix j (u ⌢ w) ⊨n ν')"
by simp
ultimately
show ?case
by simp (metis (full_types) le_antisym prefix_suffix semantics_ltln.simps(2) suffix_0 suffix_conc_length suffix_suffix zero_le)
next
case (StrongRelease_ltln ν ν')
hence "∃i. suffix i (u ⌢ w) ⊨n ν ∧ (∀j≤i. suffix j (u ⌢ w) ⊨n ν')"
using semantics_ltln.simps(11) by blast
thus ?case
by simp (metis StrongRelease_ltln(1-3) diff_is_0_eq nat_le_linear prefix_conc_length prefix_suffix pure_universal.simps(8) subsequence_length suffix_conc_snd suffix_subseq_join)
next
case (Next_ltln μ)
thus ?case
by (metis prefix_suffix pure_universal.simps(9) semantics_ltln.simps(7) semiring_normalization_rules(24) suffix_conc_length suffix_suffix)
qed auto
lemma suspendable_prefix_invariant:
"suspendable ξ ==> (u ⌢ w) ⊨n ξ ⟷ w ⊨n ξ"
proof (induction ξ arbitrary: u w)
case (Until_ltln ξ ξ')
show ?case
proof (cases "suspendable ξ'")
case False
hence "ξ = truen" and "pure_universal ξ'"
using Until_ltln by simp+
thus ?thesis
by (simp; metis (no_types) linear pure_universal_suffix_closed suffix_conc_fst suffix_conc_length suffix_conc_snd suffix_suffix)
qed (simp; metis Until_ltln(2) not_less0 prefix_suffix)
next
case (Release_ltln ξ ξ')
show ?case
proof (cases "suspendable ξ'")
case False
hence "ξ = falsen" and "pure_eventual ξ'"
using Release_ltln by simp+
thus ?thesis
by (simp; metis (no_types) le_iff_add add_diff_cancel_left' linear pure_eventual_left_append suffix_0 suffix_conc_fst suffix_conc_snd)
qed (simp; metis Release_ltln(2) not_less0 prefix_suffix)
next
case (WeakUntil_ltln ξ ξ')
show ?case
proof (cases "suspendable ξ ∧ suspendable ξ'")
case False
hence "ξ' = falsen" and "pure_eventual ξ"
using WeakUntil_ltln by simp+
thus ?thesis
by (simp; metis (no_types) le_iff_add add_diff_cancel_left' linear pure_eventual_left_append suffix_0 suffix_conc_fst suffix_conc_snd)
qed (simp; metis (full_types) WeakUntil_ltln.IH prefix_suffix)
next
case (StrongRelease_ltln ξ ξ')
show ?case
proof (cases "suspendable ξ ∧ suspendable ξ'")
case False
hence "ξ' = truen" and "pure_universal ξ"
using StrongRelease_ltln by simp+
thus ?thesis
by (simp; metis (no_types) linear pure_universal_suffix_closed suffix_conc_fst suffix_conc_length suffix_conc_snd suffix_suffix)
qed (simp; metis (full_types) StrongRelease_ltln.IH(1) StrongRelease_ltln.IH(2) prefix_suffix)
qed (simp_all, metis prefix_suffix)
theorem pure_eventual_until_simp:
assumes "pure_eventual μ"
shows "w ⊨n φ Un μ ⟷ w ⊨n μ"
proof -
have "∧i. suffix i w ⊨n μ ==> w ⊨n μ"
using pure_eventual_left_append[OF assms] prefix_suffix by metis
thus ?thesis
by force
qed
theorem pure_universal_release_simp:
assumes "pure_universal ν"
shows "w ⊨n φ Rn ν ⟷ w ⊨n ν"
proof -
have "∧i. w ⊨n ν ==> suffix i w ⊨n ν"
using pure_universal_suffix_closed[OF assms] prefix_suffix by metis
thus ?thesis
by force
qed
theorem pure_universal_weak_until_simp:
assumes "pure_universal φ" and "pure_universal ψ"
shows "w ⊨n φ Wn ψ ⟷ w ⊨n φ orn ψ"
proof -
have "∧i. w ⊨n φ ==> suffix i w ⊨n φ" and "∧i. w ⊨n ψ ==> suffix i w ⊨n ψ"
using assms pure_universal_suffix_closed prefix_suffix by metis+
thus ?thesis
by force
qed
theorem pure_eventual_strong_release_simp:
assumes "pure_eventual φ" and "pure_eventual ψ"
shows "w ⊨n φ Mn ψ ⟷ w ⊨n φ andn ψ"
proof -
have "∧i. suffix i w ⊨n φ ==> w ⊨n φ" and "∧i. suffix i w ⊨n ψ ==> w ⊨n ψ"
using assms pure_eventual_left_append prefix_suffix by metis+
thus ?thesis
by force
qed
theorem suspendable_formula_simp:
assumes "suspendable ξ"
shows "w ⊨n Xn ξ ⟷ w ⊨n ξ" (is ?t1)
and "w ⊨n φ Un ξ ⟷ w ⊨n ξ" (is ?t2)
and "w ⊨n φ Rn ξ ⟷ w ⊨n ξ" (is ?t3)
proof -
have "∧i. suffix i w ⊨n ξ ⟷ w ⊨n ξ"
using suspendable_prefix_invariant[OF assms] prefix_suffix by metis
thus ?t1 ?t2 ?t3
by force+
qed
theorem suspendable_formula_simp2:
assumes "suspendable φ" and "suspendable ψ"
shows "w ⊨n φ Wn ψ ⟷ w ⊨n φ orn ψ" (is ?t1)
and "w ⊨n φ Mn ψ ⟷ w ⊨n φ andn ψ" (is ?t2)
proof -
have "∧i. suffix i w ⊨n φ ⟷ w ⊨n φ" and "∧i. suffix i w ⊨n ψ ⟷ w ⊨n ψ"
using assms suspendable_prefix_invariant prefix_suffix by metis+
thus ?t1 ?t2
by force+
qed
fun rewrite_modal :: "'a ltln → 'a ltln"
where
"rewrite_modal truen = truen"
| "rewrite_modal falsen = falsen"
| "rewrite_modal (φ andn ψ) = (rewrite_modal φ andn rewrite_modal ψ)"
| "rewrite_modal (φ orn ψ) = (rewrite_modal φ orn rewrite_modal ψ)"
| "rewrite_modal (φ Un ψ) = (if pure_eventual ψ ∨ suspendable ψ then rewrite_modal ψ else (rewrite_modal φ Un rewrite_modal ψ))"
| "rewrite_modal (φ Rn ψ) = (if pure_universal ψ ∨ suspendable ψ then rewrite_modal ψ else (rewrite_modal φ Rn rewrite_modal ψ))"
| "rewrite_modal (φ Wn ψ) = (if pure_universal φ ∧ pure_universal ψ ∨ suspendable φ ∧ suspendable ψ then (rewrite_modal φ orn rewrite_modal ψ) else (rewrite_modal φ Wn rewrite_modal ψ))"
| "rewrite_modal (φ Mn ψ) = (if pure_eventual φ ∧ pure_eventual ψ ∨ suspendable φ ∧ suspendable ψ then (rewrite_modal φ andn rewrite_modal ψ) else (rewrite_modal φ Mn rewrite_modal ψ))"
| "rewrite_modal (Xn φ) = (if suspendable φ then rewrite_modal φ else Xn (rewrite_modal φ))"
| "rewrite_modal φ = φ"
lemma rewrite_modal_sound [simp]:
"w ⊨n rewrite_modal φ ⟷ w ⊨n φ"
proof (induction φ arbitrary: w)
case (Until_ltln φ ψ)
thus ?case
apply (cases "pure_eventual ψ ∨ suspendable ψ")
apply (insert pure_eventual_until_simp[of ψ] suspendable_formula_simp[of ψ])
apply fastforce+
done
next
case (Release_ltln φ ψ)
thus ?case
apply (cases "pure_universal ψ ∨ suspendable ψ")
apply (insert pure_universal_release_simp[of ψ] suspendable_formula_simp[of ψ])
apply fastforce+
done
next
case (WeakUntil_ltln φ ψ)
thus ?case
apply (cases "pure_universal φ ∧ pure_universal ψ ∨ suspendable φ ∧ suspendable ψ")
apply (insert pure_universal_weak_until_simp[of φ ψ] suspendable_formula_simp2[of φ ψ])
apply fastforce+
done
next
case (StrongRelease_ltln φ ψ)
thus ?case
apply (cases "pure_eventual φ ∧ pure_eventual ψ ∨ suspendable φ ∧ suspendable ψ")
apply (insert pure_eventual_strong_release_simp[of φ ψ] suspendable_formula_simp2[of φ ψ])
apply fastforce+
done
next
case (Next_ltln φ)
thus ?case
apply (cases "suspendable φ")
apply (insert suspendable_formula_simp[of φ])
apply fastforce+
done
qed auto
lemma rewrite_modal_size:
"size (rewrite_modal φ) ≤ size φ"
by (induction φ) auto
subsection ‹Syntactical Implication Based Simplification›
inductive syntactical_implies :: "'a ltln → 'a ltln → bool" (‹_ ⊨s _› [80, 80])
where
"_ ⊨s truen"
| "falsen ⊨s _"
| "φ = φ ==> φ ⊨s φ"
| "φ ⊨s χ ==> (φ andn ψ) ⊨s χ"
| "ψ ⊨s χ ==> (φ andn ψ) ⊨s χ"
| "φ ⊨s ψ ==> φ ⊨s χ ==> φ ⊨s (ψ andn χ)"
| "φ ⊨s ψ ==> φ ⊨s (ψ orn χ)"
| "φ ⊨s χ ==> φ ⊨s (ψ orn χ)"
| "φ ⊨s χ ==> ψ ⊨s χ ==> (φ orn ψ) ⊨s χ"
| "φ ⊨s χ ==> φ ⊨s (ψ Un χ)"
| "φ ⊨s χ ==> ψ ⊨s χ ==> (φ Un ψ) ⊨s χ"
| "φ ⊨s χ ==> ψ ⊨s ν ==> (φ Un ψ) ⊨s (χ Un ν)"
| "χ ⊨s φ ==> (ψ Rn χ) ⊨s φ"
| "χ ⊨s φ ==> χ ⊨s ψ ==> χ ⊨s (φ Rn ψ)"
| "φ ⊨s χ ==> ψ ⊨s ν ==> (φ Rn ψ) ⊨s (χ Rn ν)"
| "(falsen Rn φ) ⊨s ψ ==> (falsen Rn φ) ⊨s Xn ψ"
| "φ ⊨s (truen Un ψ) ==> (Xn φ) ⊨s (truen Un ψ)"
| "φ ⊨s ψ ==> (Xn φ) ⊨s (Xn ψ)"
lemma syntactical_implies_correct:
"φ ⊨s ψ ==> w ⊨n φ ==> w ⊨n ψ"
by (induction arbitrary: w rule: syntactical_implies.induct; auto; force)
fun rewrite_syn_imp
where
"rewrite_syn_imp (φ andn ψ) = (
if φ ⊨s ψ then
rewrite_syn_imp φ
else if ψ ⊨s φ then
rewrite_syn_imp ψ
else if φ ⊨s (notn ψ) ∨ ψ ⊨s (notn φ) then
falsen
else
mk_and (rewrite_syn_imp φ) (rewrite_syn_imp ψ))"
| "rewrite_syn_imp (φ orn ψ) = (
if φ ⊨s ψ then
rewrite_syn_imp ψ
else if ψ ⊨s φ then
rewrite_syn_imp φ
else if (notn φ) ⊨s ψ ∨ (notn ψ) ⊨s φ then
truen
else
mk_or (rewrite_syn_imp φ) (rewrite_syn_imp ψ))"
| "rewrite_syn_imp (φ Un ψ) = (
if φ ⊨s ψ then
rewrite_syn_imp ψ
else if (notn φ) ⊨s ψ then
mk_finally (rewrite_syn_imp ψ)
else
mk_until (rewrite_syn_imp φ) (rewrite_syn_imp ψ))"
| "rewrite_syn_imp (φ Rn ψ) = (
if ψ ⊨s φ then
rewrite_syn_imp ψ
else if ψ ⊨s (notn φ) then
mk_globally (rewrite_syn_imp ψ)
else
mk_release (rewrite_syn_imp φ) (rewrite_syn_imp ψ))"
| "rewrite_syn_imp (Xn φ) = mk_next (rewrite_syn_imp φ)"
| "rewrite_syn_imp φ = φ"
lemma rewrite_syn_imp_sound:
"w ⊨n rewrite_syn_imp φ ⟷ w ⊨n φ"
proof (induction φ arbitrary: w)
case And_ltln
thus ?case
by (simp add: Let_def; metis syntactical_implies_correct notn_semantics)
next
case (Or_ltln φ ψ)
moreover
have "(notn φ) ⊨s ψ ==> ∀w. w ⊨n φ orn ψ"
by (auto intro: syntactical_implies_correct[of "notn φ"])
moreover
have "(notn ψ) ⊨s φ ==> ∀w. w ⊨n φ orn ψ"
by (auto intro: syntactical_implies_correct[of "notn ψ"])
ultimately
show ?case
by (auto intro: syntactical_implies_correct)
next
case (Until_ltln φ ψ)
moreover
have "φ ⊨s ψ ==> ?case"
by (force simp add: Until_ltln dest: syntactical_implies_correct)
moreover
{
assume A: "(notn φ) ⊨s ψ" and B: "¬ φ ⊨s ψ"
hence [simp]: "rewrite_syn_imp (φ Un ψ) = mk_finally (rewrite_syn_imp ψ)"
by simp
{
assume "∃i. suffix i w ⊨n ψ"
moreover
define i where "i ≡ LEAST i. suffix i w ⊨n ψ"
ultimately
have "∀j < i. ¬suffix j w ⊨n ψ" and "suffix i w ⊨n ψ"
by (blast dest: not_less_Least , metis LeastI ‹∃i. suffix i w ⊨n ψ› i_def)
hence "∀j < i. suffix j w ⊨n φ" and "suffix i w ⊨n ψ"
using syntactical_implies_correct[OF A] by auto
}
hence ?case
by (simp del: rewrite_syn_imp.simps; unfold Until_ltln(2)) blast
}
ultimately
show ?case
by fastforce
next
case (Release_ltln φ ψ)
moreover
have "ψ ⊨s φ ==> ?case"
by (force simp add: Release_ltln dest: syntactical_implies_correct)
moreover
{
assume A: "ψ ⊨s (notn φ)" and B: "¬ ψ ⊨s φ"
hence [simp]: "rewrite_syn_imp (φ Rn ψ) = mk_globally (rewrite_syn_imp ψ)"
by simp
{
assume "∃i. ¬suffix i w ⊨n ψ"
moreover
define i where "i ≡ LEAST i. ¬suffix i w ⊨n ψ"
ultimately
have "∀j < i. suffix j w ⊨n ψ" and "¬ suffix i w ⊨n ψ"
by (blast dest: not_less_Least , metis LeastI ‹∃i. ¬suffix i w ⊨n ψ› i_def)
hence "∀j < i. ¬suffix j w ⊨n φ" and "¬ suffix i w ⊨n ψ"
using syntactical_implies_correct[OF A] by auto
}
hence ?case
by (simp del: rewrite_syn_imp.simps; unfold Release_ltln(2)) blast
}
ultimately
show ?case
by fastforce
qed auto
subsection ‹Iterated Rewriting›
fun iterate
where
"iterate f x 0 = x"
| "iterate f x (Suc n) = (let x' = f x in if x = x' then x else iterate f x' n)"
definition
"rewrite_iter_fast φ ≡ iterate (rewrite_modal o rewrite_X) φ (size φ)"
definition
"rewrite_iter_slow φ ≡ iterate (rewrite_syn_imp o rewrite_modal o rewrite_X) φ (size φ)"
text ‹The rewriting functions defined in the previous subsections can be used as-is. However, in the
most cases one wants to iterate these rules until the formula cannot be simplified further.
@{const rewrite_iter_fast} pulls X operators up in the syntax tree and the uses the
"modal" simplification rules. @{const rewrite_iter_slow} additionally tries to simplify the
formula using syntactic implication checking.›
lemma iterate_sound:
assumes "∧φ. w ⊨n f φ ⟷ w ⊨n φ"
shows "w ⊨n iterate f φ n ⟷ w ⊨n φ"
by (induction n arbitrary: φ; simp add: assms Let_def)
theorem rewrite_iter_fast_sound [simp]:
"w ⊨n rewrite_iter_fast φ ⟷ w ⊨n φ"
using iterate_sound[of _ "rewrite_modal o rewrite_X"]
unfolding comp_def rewrite_modal_sound rewrite_X_sound rewrite_iter_fast_def
by blast
theorem rewrite_iter_slow_sound [simp]:
"w ⊨n rewrite_iter_slow φ ⟷ w ⊨n φ"
using iterate_sound[of _ "rewrite_syn_imp o rewrite_modal o rewrite_X"]
unfolding comp_def rewrite_modal_sound rewrite_X_sound rewrite_syn_imp_sound rewrite_iter_slow_def
by blast
subsection ‹Preservation of atoms›
lemma iterate_atoms:
assumes
"∧φ. atoms_ltln (f φ) ⊆ atoms_ltln φ"
shows
"atoms_ltln (iterate f φ n) ⊆ atoms_ltln φ"
by (induction n arbitrary: φ) (auto, metis (mono_tags, lifting) assms in_mono)
lemma rewrite_modal_atoms:
"atoms_ltln (rewrite_modal φ) ⊆ atoms_ltln φ"
by (induction φ) auto
lemma mk_and_atoms:
"atoms_ltln (mk_and φ ψ) ⊆ atoms_ltln φ ∪ atoms_ltln ψ"
by (auto simp: mk_and_def split: ltln.splits)
lemma mk_or_atoms:
"atoms_ltln (mk_or φ ψ) ⊆ atoms_ltln φ ∪ atoms_ltln ψ"
by (auto simp: mk_or_def split: ltln.splits)
lemma remove_strong_ops_atoms:
"atoms_ltln (remove_strong_ops φ) ⊆ atoms_ltln φ"
by (induction φ) auto
lemma remove_weak_ops_atoms:
"atoms_ltln (remove_weak_ops φ) ⊆ atoms_ltln φ"
by (induction φ) auto
lemma mk_finally_atoms:
"atoms_ltln (mk_finally φ) ⊆ atoms_ltln φ"
by (auto simp: mk_finally_def split: ltln.splits) (insert remove_strong_ops_atoms, fast+)
lemma mk_globally_atoms:
"atoms_ltln (mk_globally φ) ⊆ atoms_ltln φ"
by (auto simp: mk_globally_def split: ltln.splits) (insert remove_weak_ops_atoms, fast+)
lemma mk_until_atoms:
"atoms_ltln (mk_until φ ψ) ⊆ atoms_ltln φ ∪ atoms_ltln ψ"
by (auto simp: mk_until_def split: ltln.splits) (insert mk_finally_atoms, fastforce+)
lemma mk_release_atoms:
"atoms_ltln (mk_release φ ψ) ⊆ atoms_ltln φ ∪ atoms_ltln ψ"
by (auto simp: mk_release_def split: ltln.splits) (insert mk_globally_atoms, fastforce+)
lemma mk_weak_until_atoms:
"atoms_ltln (mk_weak_until φ ψ) ⊆ atoms_ltln φ ∪ atoms_ltln ψ"
by (auto simp: mk_weak_until_def split: ltln.splits) (insert mk_globally_atoms, fastforce+)
lemma mk_strong_release_atoms:
"atoms_ltln (mk_strong_release φ ψ) ⊆ atoms_ltln φ ∪ atoms_ltln ψ"
by (auto simp: mk_strong_release_def split: ltln.splits) (insert mk_finally_atoms, fastforce+)
lemma mk_next_atoms:
"atoms_ltln (mk_next φ) = atoms_ltln φ"
by (auto simp: mk_next_def split: ltln.splits)
lemma mk_next_pow_atoms:
"atoms_ltln (mk_next_pow n φ) = atoms_ltln φ"
by (induction n) (auto simp: mk_next_pow_def split: ltln.splits)
lemma combine_atoms:
assumes
"∧φ ψ. atoms_ltln (f φ ψ) ⊆ atoms_ltln φ ∪ atoms_ltln ψ"
shows
"atoms_ltln (fst (combine f x y)) ⊆ atoms_ltln (fst x) ∪ atoms_ltln (fst y)"
by (metis assms fst_combine mk_next_pow_atoms prod.collapse)
lemmas combine_mk_atoms =
combine_atoms[OF mk_and_atoms]
combine_atoms[OF mk_or_atoms]
combine_atoms[OF mk_until_atoms]
combine_atoms[OF mk_release_atoms]
combine_atoms[OF mk_weak_until_atoms]
combine_atoms[OF mk_strong_release_atoms]
lemma rewrite_X_enat_atoms:
"atoms_ltln (fst (rewrite_X_enat φ)) ⊆ atoms_ltln φ"
by (induction φ) (simp_all add: case_prod_beta, insert combine_mk_atoms, fast+)
lemma rewrite_X_atoms:
"atoms_ltln (rewrite_X φ) ⊆ atoms_ltln φ"
by (induction φ) (simp_all add: rewrite_X_def mk_next_pow_atoms case_prod_beta, insert combine_mk_atoms, fast+)
lemma rewrite_syn_imp_atoms:
"atoms_ltln (rewrite_syn_imp φ) ⊆ atoms_ltln φ"
proof (induction φ)
case (And_ltln φ1 φ2)
then show ?case
using mk_and_atoms by simp fast
next
case (Or_ltln φ1 φ2)
then show ?case
using mk_or_atoms by simp fast
next
case (Next_ltln φ)
then show ?case
using mk_next_atoms by simp fast
next
case (Until_ltln φ1 φ2)
then show ?case
using mk_finally_atoms mk_until_atoms by simp fast
next
case (Release_ltln φ1 φ2)
then show ?case
using mk_globally_atoms mk_release_atoms by simp fast
qed simp_all
lemma rewrite_iter_fast_atoms:
"atoms_ltln (rewrite_iter_fast φ) ⊆ atoms_ltln φ"
proof -
have 1: "∧φ. atoms_ltln (rewrite_modal (rewrite_X φ)) ⊆ atoms_ltln φ"
using rewrite_modal_atoms rewrite_X_atoms by force
show ?thesis
by (simp add: rewrite_iter_fast_def 1 iterate_atoms)
qed
lemma rewrite_iter_slow_atoms:
"atoms_ltln (rewrite_iter_slow φ) ⊆ atoms_ltln φ"
proof -
have 1: "∧φ. atoms_ltln (rewrite_syn_imp (rewrite_modal (rewrite_X φ))) ⊆ atoms_ltln φ"
using rewrite_syn_imp_atoms rewrite_modal_atoms rewrite_X_atoms by force
show ?thesis
by (simp add: rewrite_iter_slow_def 1 iterate_atoms)
qed
subsection ‹Simplifier›
text ‹We now define a convenience wrapper for the rewriting engine›
datatype mode = Nop | Fast | Slow
fun simplify :: "mode → 'a ltln → 'a ltln"
where
"simplify Nop = id"
| "simplify Fast = rewrite_iter_fast"
| "simplify Slow = rewrite_iter_slow"
theorem simplify_correct:
"w ⊨n simplify m φ ⟷ w ⊨n φ"
by (cases m) simp+
lemma simplify_atoms:
"atoms_ltln (simplify m φ) ⊆ atoms_ltln φ"
by (cases m) (insert rewrite_iter_fast_atoms rewrite_iter_slow_atoms, fastforce+)
subsection ‹Code Generation›
code_pred syntactical_implies .
export_code simplify checking
lemma "rewrite_iter_fast (Fn (Gn (Xn propn(''a'')))) = (Fn (Gn propn(''a'')))"
by eval
lemma "rewrite_iter_fast (Xn propn(''a'') Un (Xn npropn(''a''))) = Xn (propn(''a'') Un npropn(''a''))"
by eval
lemma "rewrite_iter_slow (Xn propn(''a'') Un (Xn npropn(''a''))) = Xn (Fn npropn(''a''))"
by eval
end
¤ Dauer der Verarbeitung: 0.32 Sekunden
¤
*© Formatika GbR, Deutschland
|
|
2026-11-01
|
|
|
|
|
Neuigkeiten |
| Aktuelles |
| Motto des Tages |
|
Open Source Software |
|
|
|
Jenseits des Üblichen ....
|
|
Besucherstatistik |
|
|
| Statistik |
| #Sources=1104845 |
| #Domains=499172 |
|
|