This change * moves `termination_by` and `decreasing_by` next to the function they apply to * simplify the syntax of `termination_by` * apply the `decreasing_by` goal to all goals at once, for better interactive use. See the section in `RELEASES.md` for more details and migration advise. This is a hard breaking change, requiring developers to touch every `termination_by` in their code base. We decided to still do it as a hard-breaking change, because supporting both old and new syntax at the same time would be non-trivial, and not save that much. Moreover, this requires changes to some metaprograms that developers might have written, and supporting both syntaxes at the same time would make _their_ migration harder.
73 lines
1.9 KiB
Text
73 lines
1.9 KiB
Text
namespace Mutual
|
||
|
||
mutual
|
||
inductive Tree (α : Type u) where
|
||
| node : TreeList α → Tree α
|
||
| leaf : α → Tree α
|
||
|
||
inductive TreeList (α : Type u) where
|
||
| nil : TreeList α
|
||
| cons : Tree α → TreeList α → TreeList α
|
||
end
|
||
|
||
mutual
|
||
def Tree.size : Tree α → Nat
|
||
| Tree.node l =>
|
||
-- see "TODO: linarith" in Init.WFTactics
|
||
have : sizeOf l < 1 + sizeOf l := by
|
||
rw [Nat.add_comm]
|
||
apply Nat.lt_succ_self
|
||
sizeList l
|
||
| Tree.leaf _ => 1
|
||
-- use automatically synthesized size function, which is not quite the number of leaves
|
||
termination_by t => sizeOf t
|
||
|
||
def Tree.sizeList : TreeList α → Nat
|
||
| TreeList.nil => 0
|
||
| TreeList.cons t l =>
|
||
have : sizeOf t < 1 + sizeOf t + sizeOf l := by
|
||
rw [Nat.add_comm 1, Nat.add_assoc, Nat.add_comm 1, ← Nat.add_assoc]
|
||
apply Nat.lt_succ_of_le
|
||
apply Nat.le_add_right
|
||
have : sizeOf l < 1 + sizeOf t + sizeOf l := by
|
||
rw [Nat.add_comm 1, Nat.add_assoc, Nat.add_comm 1, ← Nat.add_assoc]
|
||
apply Nat.lt_succ_of_le
|
||
apply Nat.le_add_left
|
||
t.size + sizeList l
|
||
termination_by l => sizeOf l
|
||
end
|
||
|
||
end Mutual
|
||
|
||
namespace Nested
|
||
|
||
inductive Tree (α : Type u) where
|
||
| node : List (Tree α) → Tree α
|
||
| leaf : α → Tree α
|
||
|
||
mutual
|
||
def Tree.size : Tree α → Nat
|
||
| Tree.node l =>
|
||
have : sizeOf l < 1 + sizeOf l := by
|
||
rw [Nat.add_comm]
|
||
apply Nat.lt_succ_self
|
||
sizeList l
|
||
| Tree.leaf _ => 1
|
||
termination_by t => sizeOf t
|
||
|
||
def Tree.sizeList : List (Tree α) → Nat
|
||
| [] => 0
|
||
| t :: l =>
|
||
have : sizeOf t < 1 + sizeOf t + sizeOf l := by
|
||
rw [Nat.add_comm 1, Nat.add_assoc, Nat.add_comm 1, ← Nat.add_assoc]
|
||
apply Nat.lt_succ_of_le
|
||
apply Nat.le_add_right
|
||
have : sizeOf l < 1 + sizeOf t + sizeOf l := by
|
||
rw [Nat.add_comm 1, Nat.add_assoc, Nat.add_comm 1, ← Nat.add_assoc]
|
||
apply Nat.lt_succ_of_le
|
||
apply Nat.le_add_left
|
||
t.size + sizeList l
|
||
termination_by l => sizeOf l
|
||
end
|
||
|
||
end Nested
|