【发布时间】:2018-04-01 00:35:41
【问题描述】:
我想在 Coq 中使用 Program Fixpoint 或 Function 定义以下函数:
Require Import Coq.Lists.List.
Import ListNotations.
Require Import Coq.Program.Wf.
Require Import Recdef.
Inductive Tree := Node : nat -> list Tree -> Tree.
Fixpoint height (t : Tree) : nat :=
match t with
| Node x ts => S (fold_right Nat.max 0 (map height ts))
end.
Program Fixpoint mapTree (f : nat -> nat) (t : Tree) {measure (height t)} : Tree :=
match t with
Node x ts => Node (f x) (map (fun t => mapTree f t) ts)
end.
Next Obligation.
不幸的是,此时我有证明义务height t < height (Node x ts) 不知道t 是ts 的成员。
与Function 类似,而不是Program Fixpoint,只是Function 检测到问题并中止定义:
Error: the term fun t : Tree => mapTree f t can not contain a recursive call to mapTree
我希望得到In t ts → height t < height (Node x ts)的证明义务。
有没有一种不涉及重构函数定义的方法? (例如,我知道需要在此处内联 map 的定义的变通方法——我想避免这些。)
伊莎贝尔
为了证明这种期望是正确的,让我展示当我在 Isabelle 中使用 function 命令(与 Coq 的 Function 命令相关)时会发生什么:
theory Tree imports Main begin
datatype Tree = Node nat "Tree list"
fun height where
"height (Node _ ts) = Suc (foldr max (map height ts) 0)"
function mapTree where
"mapTree f (Node x ts) = Node (f x) (map (λ t. mapTree f t) ts)"
by pat_completeness auto
termination
proof (relation "measure (λ(f,t). height t)")
show "wf (measure (λ(f, t). height t))" by auto
next
fix f :: "nat ⇒ nat" and x :: nat and ts :: "Tree list" and t
assume "t ∈ set ts"
thus "((f, t), (f, Node x ts)) ∈ measure (λ(f, t). height t)"
by (induction ts) auto
qed
在终止证明中,我得到假设t ∈ set ts。
请注意,Isabelle 在这里不需要手动终止证明,以下定义可以正常工作:
fun mapTree where
"mapTree f (Node x ts) = Node (f x) (map (λ t. mapTree f t) ts)"
这是因为map 函数有一个“同余引理”的形式
xs = ys ⟹ (⋀x. x ∈ set ys ⟹ f x = g x) ⟹ map f xs = map g ys
function命令用来找出终止证明只需要考虑t ∈ set ts..
如果这样的引理不可用,例如因为我定义了
definition "map' = map"
并在mapTree 中使用它,我得到了与 Coq 中相同的不可证明的证明义务。我可以通过为map' 声明一个全等引理使其再次工作,例如使用
declare map_cong[folded map'_def,fundef_cong]
【问题讨论】:
标签: recursion coq isabelle termination