predicate IsFirstEven(evenIndex: int, lst: seq<int>)
requires 0 <= evenIndex < |lst|
requires IsEven(lst[evenIndex])
forall i :: 0 <= i < evenIndex ==> IsOdd(lst[i])
predicate IsFirstOdd(oddIndex: int, lst: seq<int>)
requires 0 <= oddIndex < |lst|
requires IsOdd(lst[oddIndex])
forall i :: 0 <= i < oddIndex ==> IsEven(lst[i])
method FirstEvenOddIndices(lst : seq<int>) returns (evenIndex: int, oddIndex : int)
requires exists i :: 0 <= i < |lst| && IsEven(lst[i])
requires exists i :: 0 <= i < |lst| && IsOdd(lst[i])
ensures 0 <= evenIndex < |lst|
ensures 0 <= oddIndex < |lst|
ensures IsEven(lst[evenIndex]) && IsFirstEven(evenIndex, lst)
ensures IsOdd(lst[oddIndex]) && IsFirstOdd(oddIndex, lst)
invariant 0 <= i <= |lst|
invariant forall j :: 0 <= j < i ==> IsOdd(lst[j])
invariant 0 <= i <= |lst|
invariant forall j :: 0 <= j < i ==> IsEven(lst[j])
method ProductEvenOdd(lst: seq<int>) returns (product : int)
requires exists i :: 0 <= i < |lst| && IsEven(lst[i])
requires exists i :: 0 <= i < |lst| && IsOdd(lst[i])
ensures exists i, j :: 0 <= i < |lst| && IsEven(lst[i]) && IsFirstEven(i, lst) &&
0 <= j < |lst| && IsOdd(lst[j]) && IsFirstOdd(j, lst) && product == lst[i] * lst[j]
var evenIndex, oddIndex := FirstEvenOddIndices(lst);
product := lst[evenIndex] * lst[oddIndex];