Functional programming 如何提取Isabelle中的实例化变量?

Functional programming 如何提取Isabelle中的实例化变量?,functional-programming,isabelle,theorem-proving,Functional Programming,Isabelle,Theorem Proving,我试图在伊莎贝尔身上证明以下几点: theorem map_fold: "∃h b. (map f xs) = foldr h xs b" apply (induction xs) apply auto done 如何获得h和b的实例化值?一种方法是使用SOME: h := SOME h. ∃b. map f xs = foldr h xs b b := SOME b. map f xs = foldr h xs b 使用你的map\u fold定理和一些摆弄someI\u ex,你可以证

我试图在伊莎贝尔身上证明以下几点:

theorem map_fold: "∃h b. (map f xs)  = foldr h xs b"
apply (induction xs)
apply auto
done

如何获得
h
b
的实例化值?

一种方法是使用
SOME

h := SOME h. ∃b. map f xs = foldr h xs b
b := SOME b. map f xs = foldr h xs b
使用你的
map\u fold
定理和一些摆弄
someI\u ex
,你可以证明用这些定义,
map f xs=foldr h xs b
确实成立

然而,虽然这在逻辑上为您提供了
h
b
的值,但我希望您不会对它们非常满意,因为您实际上看不到
h
b
是什么;而且(逻辑上)也没有办法做到这一点

在某些情况下,您还可以制定一个定理,说明“有
f
xs
,这样就没有
h
b
map f xs=foldr h xs b
一起存在了”,并进行挑剔以找到该语句的反例,但这种情况太复杂,无法挑剔,因为它必须在无限域上找到一个函数,这个函数依赖于无限域上的另一个函数

我不认为有什么方法可以让你从你证明为具体值的定理中,得到存在的见证人
h
b
。您只需通过检查感应情况来找到它们,并发现它们是
h=λx xs。f x#xs
b=[]

这是迄今为止最简单的解决方案

更新:证据提取 今天重读这篇文章时,我真的记得在伊莎贝尔身上确实存在证据提取。它要求为所有定理计算明确的证明项,因此您需要以Isabelle jedit-l HOL证明开始Isabelle。然后你可以这样做:

theorem map_fold: "∃h b. (map f xs)  = foldr h xs b"
  by (induction xs) auto

extract map_fold
这将定义类型为
('a)的常量
映射
⇒ '(b)⇒ '单子⇒ ('a⇒ 'b名单⇒ 'b list)×b list
,即给定一个映射函数和一个列表,它为您提供了函数和初始状态,您必须将其放入
foldr
,以获得相同的结果。您可以使用
thm map\u fold\u def
查看定义。稍微简化一下,它看起来是这样的:

map_fold f xs = 
    rec_list (λx xa. default, []) (λx xa H. (λa b. f a # map f xa, default)) xs
这有点难读,但您可以看到
[]
fa#map f xa


不幸的是,证明术语变得相当大,因此我怀疑这对于玩具示例以外的任何东西都没有多大用处。

有时用于此目的的方法是陈述一个示意引理:

schematic_lemma "map f xs = foldr ?h xs ?b"
apply (induct xs)
apply simp
...
类似于
simp
rule
的方法可以在证明过程中实例化原理图变量(统一的结果)。如果您能够完成证明,那么您可以只看得到的引理,看看最终的实例化是什么

请注意,原理图变量可能有点棘手:有时
simp
会实例化一个原理图变量,使当前目标很容易证明,但同时使其他子目标无法解决

在这个特定的例子中,Isabelle能够毫无问题地实例化?b,但它不能通过统一来确定?h。通常,带有函数类型的原理图变量处理起来要复杂得多


最后,我做了一些Manuel建议的事情:首先,用普通变量表示引理(
lemma“map f xs=foldr h xs b”
)。然后看看归纳法的证明在哪里被卡住了,然后逐步完善这个陈述,直到它是可证明的。

噢,当然了。我怎么没有想到图解引理呢?我一定是老了。但是,是的,原理图变量的自动实例化可能有些棘手。