∃-使用Z3定点引擎进行查询和∀查询

时间:2016-09-09 03:58:40

标签: z3 smt

我很困惑并且很难理解Z3定点引擎的两种不同输入格式是如何相关的。简短的例子:假设我想证明负数的存在。我声明一个函数,对于非负数返回1,对于负数返回0,然后如果有函数返回0的参数则要求求解器失败。但是有一个限制:我希望求解器在那里回复sat如果所有数字都是非负数,则至少存在一个负数和unsat

使用declare-relquery格式很简单:

(declare-rel f (Int Int))
(declare-rel fail ())
(declare-var n Int)
(declare-var m Int)

(rule (=> (< n 0) (f n 0)))
(rule (=> (>= n 0) (f n 1)))

(rule (=> (and (f n m) (= m 0)) fail))
(query fail)

但是使用纯SMT-LIB2格式(使用forall)时会变得棘手。例如,直截了当

(set-logic HORN)
(declare-fun f (Int Int) Bool)
(declare-fun fail () Bool)

(assert (forall ((n Int)) 
    (=> (< n 0) (f n 0))))
(assert (forall ((n Int)) 
    (=> (>= n 0) (f n 1))))

(assert (forall ((n Int) (m Int)) 
    (=> (and (f n m) (= m 0)) fail)))
(assert (not fail))

(check-sat)

返回unsat。不出所料,将(= m 0)更改为(= m 1)会产生相同的结果。我们sat只能fail隐含(= m 2)。问题是我无法理解,如何使用这种格式询问解算器

我现在如何理解它,在使用forall形式时,我们可以要求只找到solutions解,即答案sat意味着解算器设法找到解释(或不变量) )满足所有值的所有断言,unsat表示没有这样的函数。换句话说,它试图证明,将'证明'(不变量)放入模型中(显然,当sat时)。

相反,当query格式解算器中的declare-rel解决方案搜索解决方案中的某些变量时,就像约束在∃量词下一样。换句话说,它给出了反例。它只能在unsat

的情况下打印不变量

我有几个问题:

  1. 我理解正确吗?我觉得我想念一些关键的想法。例如,如何用(query ...)来表达(assert (forall ...))的一般概念将非常有用(并将自动回答问题2)。
  2. 有没有办法用纯SMT-LIB2格式解决这种∃约束(在发现反例时输出sat)?如果是,那么如何?

1 个答案:

答案 0 :(得分:3)

首先,使用&#34; declare-rel&#34;,&#34; declare-var&#34;,&#34; rule&#34;和&#34;查询&#34;是SMT-LIB2的自定义扩展。 &#34; declare-var&#34;功能可以方便地从多个规则中省略绑定变量。它还允许使用分层否定来制定Datalog规则,并且这是您应该从分层否定中获得的语​​义。按惯例,它使用&#34; sat&#34;表示查询具有派生,并且&#34;不满&#34;不存在查询的派生。

事实证明,标准SMT-LIB2可以表达您想要的东西 Horn条款没有否定。规则成为含义,查询是形式的含义:(=&gt;查询错误),或者在您编写时(不是查询)。 自定义格式的推导对应于空子句的证明(例如,&#34;查询&#34;的证明,然后证明&#34;假&#34;)。因此,推导的存在意味着SMT-LIB2断言是'不饱和的'#34;。相反,如果对Horn条款有解释(模型),那么这样的模型确定没有推导。这些条款是&#34; sat&#34;。

换句话说:

 "sat" for datalog extension   <=> "unsat" for SMT-LIB2 formulation
 "unsat" for datalog extension <=> "sat" for SMT-LIB2 formulation

使用纯SMT-LIB2格式的优点是,适用时 没有特殊的语法扩展。这些是简单的SMT公式和 其他希望解决这类公式的人不必写特别的 扩展,他们只需要确保调整到的解算器 Horn条款承认适当的公式。 (Z3&#39;实施 HORN片段确实​​允许在写下Horn子句时有一定的灵活性。 你可以在身体中分离,你可以有Curried的含义。

使用基于规则的格式有助于的SMT-LIB2格式有一个缺点:当存在查询的派生时,基于规则的格式具有用于打印元组元素的编译指示。请注意,通常查询关系可以带参数。此功能对于有限域关系很有用。 上面的示例使用整数,因此关系不是有限域,但在线教程中的示例包含有限域实例。 现在,查询的推导也对应于分辨率证明。您可以从SMT-LIB2案例中提取分辨率证明,但我不得不说它是相反的 令人费解,我还没有找到一种有效使用它的方法。 &#34;二元性&#34; Horn子句的引擎以更易于访问的格式生成派生 Z3的默认证明格式。无论哪种方式,如果用户尝试使用证明证书,很可能会遇到障碍,因为他们很少使用。基于规则的格式确实具有另一个功能,该功能使用与派生路径对应的实例组合一组谓词。这个输出更容易观察。