Isabelle书练习2.11:将表达式转换为多项式形式

时间:2016-05-16 17:00:24

标签: isabelle theorem-proving

我的问题是关于具体语义学(http://concrete-semantics.org/)一书中的练习2.11:

在整数中定义一个变量中的算术表达式 (键入int)作为数据类型:

datatype exp = Var | Const int | Add exp exp | Mult exp exp

定义一个函数eval :: exp => int => int,以便eval e x评估e at 值x。 多项式可以表示为系数列表,从 不变。例如,[4,2,-1,3]表示多项式4+2x-x^2+3x^3

定义一个函数evalp :: int list => int => int,用于计算多项式 给定的值。定义一个转换的函数coeffs :: exp => int list 表达成多项式。这可能需要辅助功能。证明 coeffs保留表达式的值:evalp (coeffs e) x = eval e x

---端

在你到达coeffs之前,这一切都非常简单。我们必须处理像(X + X)*(2*X + 3*X*X)这样的表达式,这些表达式必须使用分布式法则自下而上地递增扩展,直到它以多项式形式。结果表达式可能仍然类似于(X*X + X*2*X + 3*X*X + 4*X*X*X),因此必须对产品术语进行标准化(例如X*2*X变为2*X*X),像术语一样收集,最后按增加的顺序排序学位!到目前为止,这似乎比任何练习都要复杂得多,我想知道我是否遗漏了某些内容或过于复杂。

1 个答案:

答案 0 :(得分:3)

我认为这项练习比你想象的容易得多。你可以写一个完成工作的原始递归函数coeffsVar的系数是[0,1]Const c的系数是[c]。类似地,如果您有两个子表达式并且您知道它们的系数,则可以将这两个系数列表组合成一个列表以进行加法/乘法。

为此,理想情况下应编写两个辅助函数add_coeffsmult_coeffs,它们将两个系数列表相加和相乘。 (后者可能会利用前者)

您必须证明add_coeffsmult_coeffs做正确的事(w.r.t。evalevalp)。由此产生的引理也会产生良好的[simp]规则。

证据都是简单的导入,每个案例都是自动的。

作为一般规则:良好的定义通常会使长而乏味的证据与直接甚至完全自动的证明之间产生差异。如您在问题中所建议的那样,进行冗长的扩展,然后对求和等进行分组,这肯定会导致一个单调乏味的证明。

当然,我在这个答案中建议的方法不是很有效,但是当你想在一个定理证明器中做事时,效率通常不是一个大问题 - 你希望事情简单而优雅,并且适合于很好的证明。如果你需要高效的代码,你仍然可以将你漂亮而简单的抽象公式开发成更高效的东西,并显示出等效性。