最后注释掉的assert不会验证,但是运行上述if语句时将显示。 输出
ohb= true
ohx= false
palin(xe) == false
ohx ==false
function method palin(a:seq<int>) :bool {
forall i:int :: (0<=i && i<(|a|/2)) ==> a[i]==a[|a|-i -1]
}
method Main() {
var xe:seq<int> := [0,1,2,3,0];
var se:seq<int> := [0,1,2,1,0];
var ohb := palin(se);
var ohx :bool := palin(xe);
print "ohb= ",ohb,"\n";
print "ohx= ",ohx,"\n";
assert palin(se);
if (palin(xe) == false) {print "palin(xe) == false\n";}
if (!ohx) {print "ohx ==false\n";}
//assert !ohx;
}
答案 0 :(得分:1)
断言失败意味着验证者无法自动找到证明。如果您认为该财产有效,则需要编写证明(或证明的一部分)。
对于您的程序,证明某些东西不是回文,可以归结为显示违反回文属性的职位。从逻辑上讲,您正在尝试证明forall
是exists
的否定,并且为了证明exists
您需要为边界提供证人变量i
。
在您的示例中,满足以下条件:
predicate method palin(a: seq<int>) {
forall i :: 0 <= i < |a| / 2 ==> a[i] == a[|a| - i - 1]
}
method Main() {
var xe := [0,1,2,3,0];
var se := [0,1,2,1,0];
var ohb := palin(se);
var ohx := palin(xe);
print "ohb= ", ohb, "\n";
print "ohx= ", ohx, "\n";
assert palin(se);
if palin(xe) == false { print "palin(xe) == false\n"; }
if !ohx { print "ohx == false\n"; }
assert !ohx by {
assert xe[1] != xe[3];
}
}