规格:
package PolyPack with SPARK_Mode is
type Vector is array (Natural range <>) of Integer;
function RuleHorner (X: Integer; A : Vector) return Integer
with
Pre => A'Length > 0 and A'Last < Integer'Last;
end PolyPack ;
我想用Assert和loop_invariants编写PolyPack软件包的主体,以便gnatprove程序可以证明我的函数RuleHorner正确性。
我编写了函数Horner,但我不知道如何在程序中放置断言和loop_invariants来证明其核心:
with Ada.Integer_Text_IO;
package body PolyPack with SPARK_Mode is
function RuleHorner (X: Integer; A : Vector) return Integer is
Y : Integer := 0;
begin
for I in 0 .. A'Length - 1 loop
Y := (Y*X) + A(A'Last - I);
end loop;
return Y;
end RuleHorner ;
end PolyPack ;
gnatprove:
overflow check might fail (e.g. when X = 2 and Y = -2)
overflow check might fail
溢出检查适用于Y行:=(Y * X)+ A(A'Last-I);
有人可以帮我如何使用loop_invariants删除溢出检查
答案 0 :(得分:3)
分析是正确的。 Vector类型的元素类型为Integer。当X = 2,Y = -2,并且A(A'Last-I)小于Integer'First + 4时,将发生下溢。您认为如何在程序中处理此问题?循环不变式在这里不起作用,因为您无法证明不会发生上溢或下溢。 有没有一种方法可以设计Vector中使用的类型和/或子类型以及变量X和Y,以防止Y上溢或下溢?
我也很好奇为什么要忽略Vector中的最后一个值。您是否要反向遍历阵列?如果是这样,只需使用以下for循环语法:
for I in reverse A'Range loop