Z3 MBQI同一模型的API和SMT-LIB之间的不同行为

Z3 MBQI同一模型的API和SMT-LIB之间的不同行为,z3,Z3,我用Z3来检查一些量化公式。如果我通过Z3的JavaAPI断言该公式,那么如果该公式是unsat的,MBQI引擎可能不会收敛。我知道我的公式不在已知可判定的FOL片段中,但是如果我通过Z3的smt lib接口输入相同的公式,它会很快生成答案。我怀疑某些选项没有通过API设置,而该API通常在正常SMTLIB输入中处于活动状态,或者我没有通过API向公式中添加重要的元信息 以下SMTLIB会话中的断言直接取自我通过API断言的BoolExpr的toString: (set-option :smt.

我用Z3来检查一些量化公式。如果我通过Z3的JavaAPI断言该公式,那么如果该公式是unsat的,MBQI引擎可能不会收敛。我知道我的公式不在已知可判定的FOL片段中,但是如果我通过Z3的smt lib接口输入相同的公式,它会很快生成答案。我怀疑某些选项没有通过API设置,而该API通常在正常SMTLIB输入中处于活动状态,或者我没有通过API向公式中添加重要的元信息

以下SMTLIB会话中的断言直接取自我通过API断言的BoolExpr的toString:

(set-option :smt.mbqi true)
(set-option :smt.pull-nested-quantifiers true)
(set-option :smt.mbqi.trace true)
(declare-fun R (Int Int) Bool)
(declare-const |'x| Int)
(declare-const |'y| Int)
(assert 
  (let ((a!1 (forall ((|'x0| Int) (|'y0| Int))
         (= (R |'x0| |'y0|)
            (and (forall ((|'y1| Int) (a Int))
                   (let ((a!1 (not (or (and (= |'y0| 0) (= |'y1| 1))
                                       (and (= |'y0| 1) (= |'y1| 3))
                                       (and (= |'y0| 2) (= |'y1| 3))
                                       (and (= |'y0| 0) (= |'y1| 2)))))
                         (a!2 (exists ((|'x1| Int))
                                (and (or (and (= |'x0| 3) (= |'x1| 0))
                                         (and (= |'x0| 1) (= |'x1| 3))
                                         (and (= |'x0| 1) (= |'x1| 2))
                                         (and (= |'x0| 2) (= |'x1| 0))
                                         (and (= |'x0| 0) (= |'x1| 1)))
                                     (R |'x1| |'y1|)))))
                     (or a!1 a!2)))
                 (forall ((|'x1| Int) (a Int))
                   (let ((a!1 (not (or (and (= |'x0| 3) (= |'x1| 0))
                                       (and (= |'x0| 1) (= |'x1| 3))
                                       (and (= |'x0| 1) (= |'x1| 2))
                                       (and (= |'x0| 2) (= |'x1| 0))
                                       (and (= |'x0| 0) (= |'x1| 1)))))
                         (a!2 (exists ((|'y1| Int))
                                (and (or (and (= |'y0| 0) (= |'y1| 1))
                                         (and (= |'y0| 1) (= |'y1| 3))
                                         (and (= |'y0| 2) (= |'y1| 3))
                                         (and (= |'y0| 0) (= |'y1| 2)))
                                     (R |'x1| |'y1|)))))
                     (or a!1 a!2))))))))
 (and (= |'x| 0) (= |'y| 0) (R |'x| |'y|) a!1)))
(check-sat)
有趣的是,当我通过Z3的SMTLIB接口运行上述命令时,MBQI跟踪很短,如下所示:

(smt.mbqi "started")
(smt.mbqi :checking k!37)
(smt.mbqi :failed k!37)
(smt.mbqi :num-failures 1)
...
(smt.mbqi "started")
(smt.mbqi :checking k!37)
(smt.mbqi :failed k!37)
(smt.mbqi :num-failures 1)
unsat
但是,通过API运行时的跟踪(以及相同的解算器选项)如下所示:

(smt.mbqi "started")
(smt.mbqi :failed null)
(smt.mbqi :num-failures 1)
(smt.mbqi "started")
(smt.mbqi :failed null)
(smt.mbqi :num-failures 1)

“null”引用是否表示我在API方面做错了什么

我在再现失败行为时遇到了一些问题。下面是我如何模拟API行为的:

从z3导入*
spec=”“”
(声明乐趣R(Int)Bool)
(声明常量|'x | Int)
(声明常数为Int)
(断言
(let((a!1)(for all((|'x0 | Int)(|'y0 | Int))
(=(R |'x0 | |'y0 |)
(和(所有(|'y1|Int)(a Int))
(让((a!1)(不是(或(=|'y0 | 0)(=|'y1 | 1))
(和(='y0 | 1)(='y1 | 3))
(和(='y0 | 2)(='y1 | 3))
(和(=|'y0 | 0)(=|'y1 | 2 |)'))
(a!2(存在(|'x1 | Int))
(和(或)(和(=|'x0 | 3)(=|'x1 | 0))
(和(=|'x0 | 1)(=|'x1 | 3))
(和(=|'x0 | 1)(=|'x1 | 2))
(和(=|'x0 | 2)(=|'x1 | 0))
(和(=|'x0 | 0)(=|'x1 | 1)))
(R |'x1 | |'y1 | | | | | | | | | | | | | | |
(或a!1 a!2)))
(对于所有(|'x1 | Int)(a Int))
(让((a!1)(不是(或(=|'x0 | 3)(=|'x1 | 0))
(和(=|'x0 | 1)(=|'x1 | 3))
(和(=|'x0 | 1)(=|'x1 | 2))
(和(=|'x0 | 2)(=|'x1 | 0))
(和(=|'x0 | 0)(=|'x1 | 1 | | | | | |)))
(a!2(存在(|'y1 | Int))
(和(或(和(=|'y0 | 0)(=|'y1 | 1))
(和(='y0 | 1)(='y1 | 3))
(和(='y0 | 2)(='y1 | 3))
(和(='y0 | 0)(='y1 | 2)))
(R |'x1 | |'y1 | | | | | | | | | | | | | | |
(或a!1 a!2()())()()))
(和(='x | 0)(='y | 0)(R |'x | y |)a!1)))
"""
spec=parse_smt2_字符串(spec)
#设置_选项(详细=10)
设置选项('smt.mbqi',真)
set_选项('smt.pull_嵌套的_量词',True)
设置选项('smt.mbqi.trace',True)
s=解算器()
s、 添加(规格)

print s.check()
空引用是因为我构造量词时没有提供量词ID。不幸的是,即使设置了量词ID,MBQI细化过程也不能使用APIKOLAJ收敛。很抱歉,我无法提供产生我的程序正在进行的API调用的确切序列。我将尝试制作一个独立的程序来复制该行为并将其发回。感谢您提供有关详细跟踪的提示。我来看看。