Lifetime-generate has additional trait bound restrictions (?)
utaal-b opened this issue · comments
Andrea Lattuada (VMware) commented
use vstd::prelude::*;
use vstd::seq_lib::*;
verus! {
trait VerusClone: View + Sized {
fn verus_clone(&self) -> (r: Self)
ensures self@ == r@;
}
fn vec_filter<V: VerusClone>(v: Vec<V>, f: impl Fn(&V)->bool, f_spec: FnSpec(V)->bool) -> (r: Vec<V>)
requires forall|v: V| #[trigger] f.requires((&v,)), forall |v:V,r:bool| f.ensures((&v,), r) ==> f_spec(v) == r,
ensures r@.to_multiset() =~= v@.to_multiset().filter(f_spec)
{
let mut r = Vec::new();
let mut i = 0;
proof { lemma_seq_properties::<V>(); }
while i < v.len()
invariant
forall|v: V| #[trigger] f.requires((&v,)),
i <= v.len(),
r@.to_multiset() =~= v@.subrange(0, i as int).to_multiset().filter(f_spec),
forall |v:V,r:bool| f.ensures((&v,), r) ==> f_spec(v) == r,
{
proof { lemma_seq_properties::<V>(); }
let ghost pre_r = r@.to_multiset();
assert(
v@.subrange(0, i as int + 1)
=~=
v@.subrange(0, i as int).push(v@[i as int]));
if f(&v[i]) {
r.push(v[i].verus_clone());
}
i += 1;
}
r
}
}
fails with
error: the trait bound `A27_V: T28_View` is not satisfied
--> vec.rs:32:20
|
32 | r.push(v[i].verus_clone());
| ____________________^^^^_^
33 | | }
| |______^
and
fn vec_filter<V: VerusClone>
needs to be
fn vec_filter<V: VerusClone + View + Sized>
Andrea Lattuada (VMware) commented
I believe this is because we ignore VerusClone
because it doesn't have any associated types, but the type checker uses it to constrain V
to be View + Sized
too.