我想用Z3 python证明两个公式'f'和'g'的等价性。 在下面的代码中,基本上'g'是'f',添加了一些随机代码。我使用Exists限定符忽略了'g'中的所有随机代码,因此'f'和'g'实际上是等价的。
MI = BitVecSort(32)
MV = BitVecSort(8)
Mem = Array('Mem', MI, MV)
def equivalence(F, G):
s = Solver()
s.add(Not(F == G))
if s.check() == unsat:
print "Equivalence"
else:
print "Inequivalence"
def Select2(M, I):
return Concat(Select(M, I+1), Select(M, I))
x, y = BitVecs('x y', 32)
g = True
t = BitVec('t', 32)
g = And(g, t == y)
t2 = BitVec('t2', 16)
g = And(g, t2 == Select2(Mem, t))
t3 = BitVec('t3', 32)
g = And(g, t3 == (t + 2))
y1 = BitVec('y1', 32)
g = And(g, y1 == t)
x1 = BitVec('x1', 32)
g = And(g, x1 == 0)
f = True
x1 = BitVec('x1', 32)
f = And(f, x1 == 0)
equivalence(Exists([t3, t2, t, y, y1, x], g), f)
然而,这个脚本返回'Inequivalence'而不是预期的“Equivalence”。实际上,仔细观察,等效的s.check()会返回“Unknown”。
我希望Z3能够轻松解决这个琐碎的问题,但似乎Z3在这里做错了。有什么想法吗?
非常感谢。
答案 0 :(得分:2)
由于量词,你得到unknown
。您可以通过应用量词消除来获得预期的答案。我们可以创建一个使用qe
和smt
求解器的求解器。我们只需要替换
s = Solver()
带
s = Then('qe', 'smt').solver()
Then
是一个组合子,它构建一个应用qe
(量词消除)的策略,然后调用通用SMT求解器smt
。方法.solver()
将策略转换为求解器。
我们可以测试它here。