Z3 - 假设如何运作

时间:2018-03-16 16:39:41

标签: z3 z3py

我在Z3py中有以下代码

    import z3
    x = z3.BitVec('x', 32)
    a = z3.BitVec('a', 32)
    solver=z3.Solver()
    solver.set(unsat_core=True)
    d=z3.Bool('d')
    solver.assert_and_track(x!=a,d)
    solver.add(x==a)
    print solver.check(d)
    print solver.check(z3.Not(d))

我希望它能打印unsatsat。但是它始终打印unsat。呼叫solver.check(z3.Not(d))是否应该有效地禁用断言x!=a

1 个答案:

答案 0 :(得分:1)

assert_and_track只是将答案文字d与您示例中的公式x!=a相关联。由于上下文同时包含x==ax!=a,因此它是unsat。没有任何假设会让它变得令人满意。

但我确实同意这很令人困惑。我认为这个问题可以追溯到这样一个事实:assert_and_track 请参阅此处的讨论:https://stackoverflow.com/a/14565535/936310

要真正实现自己想要的目标,只需自己断言。也就是说,使用:

solver.add(Implies(d, x!=a))

例如,以下脚本:

from z3 import *

x = z3.BitVec('x', 32)
a = z3.BitVec('a', 32)

solver=z3.Solver()
solver.set(unsat_core=True)
d=z3.Bool('d')

solver.add(Implies(d, x!=a))
solver.add(x==a)

print solver.check(d)
print solver.unsat_core()
print solver.check(z3.Not(d))
print solver.model()

产生

unsat
[d]
sat
[a = 0, d = False, x = 0]

这是你想要实现的目标。