我正在尝试在Boogie中对固定长度的向量建模。每个大小不同的向量都应具有不同的类型。
我尝试了两种方法,但是都有一个特殊的问题。
定义类型别名和一些描述类型别名长度的公理。但是,由于仅创建别名而不是新类型,因此公理对所有别名均有效。因此,我们得到了矛盾的公理。
function length(x: [int]real) returns (n: int);
type Vector3 = [int]real;
axiom (forall x: Vector3 :: length(x) == 3);
type Vector5 = [int]real;
// The following axiom conflicts with the previous one.
axiom (forall x: Vector5 :: length(x) == 5);
procedure impl1();
implementation impl1()
{
var v1: Vector3;
var v2: Vector5;
v1[0] := 1.0;
v1[0] := 2.0;
v1[0] := 3.0;
assert length(v1) == 3;
assert length(v2) == 5;
assert length(v1) == 999; // Must fail but it doesn't.
}
在这里,我们为每个固定长度的向量创建一个新鲜的类型,并使用标记“ Dim3”使其具有唯一性。长度使用公理来描述。这里的问题是我不知道如何访问/分配给这种类型的地图。
function length<D>(x: Vector D [int]real) returns (n: int);
type Vector alpha beta;
type Dim1;
type Dim2;
type Dim3;
type Dim4;
type Dim5;
type Vector3 = Vector Dim3 [int]real;
axiom (forall x: Vector3 :: length(x) == 3);
type Vector5 = Vector Dim5 [int]real;
axiom (forall x: Vector5 :: length(x) == 5);
procedure impl1();
implementation impl1()
{
var v1: Vector3;
var v2: Vector5;
v1[0] := 1.0; // Invalid boogie code: 'Error: map assignment applied to a non-map'
v1[0] := 2.0;
v1[0] := 3.0;
assert length(v1) == 3;
assert length(v2) == 5;
}
如果有人能指出我正确的方向,我会很高兴!