public class Relaxed {
//@ requires true;
//@ ensures pat.length == 0 ==> \result == true;
//@ ensures a.length == 0 && pat.length == 1 ==> \result == true;
//@ ensures a.length == 0 && pat.length > 1 ==> \result == false;
//@ ensures pat.length > 0 && a.length > 0 ==> Relaxed.diffIndex(pat, a) == pat.length ==> \result == true;
public static boolean isRelaxedPrefix(int[] pat, int[] a) {
int shift = 0;
int index = 0;
if (pat.length == 0) return true;
if (a.length == 0 && pat.length == 1) return true;
if (a.length == 0 && pat.length > 1) return false;
assert a.length > 0 && pat.length > 0;
if (Relaxed.diffIndex(pat, a) == pat.length) return true;
//@ maintaining 0 <= index && index <= pat.length;
//@ maintaining 0 <= index - shift && index - shift <= a.length && 0 <= shift && shift <= 1;
//@ maintaining Relaxed.diffIndex(pat, a) > index ==>(\forall int i; 0 <= i && i < index; pat[i] == a[i]) ;
//@ maintaining Relaxed.diffIndex(pat, a) > index ==> (\forall int j; Relaxed.diffIndex(pat, a) < j && j < index; pat[j] == a[j - 1]);
//@ decreases pat.length - index - shift;
while((pat.length > index ) && (a.length > index - shift)){
if (pat[index] != a[index - shift]){
if (shift == 0) shift = 1;
else return false;
}
index = index + 1;
}
if (a.length == index - shift && pat.length > index ) return false;
return true;
}
//@ requires true;
//@ ensures 0 <= \result && \result <= pat.length;
//@ ensures (\forall int i; 0 <= i && i < \result; pat[i] == a[i]);
//@ ensures (pat.length > \result) && (a.length > \result) ==> pat[\result] != a[\result];
public /*@ pure function @*/ static int diffIndex(int[] pat, int[] a)
{
int index = 0;
//@ maintaining 0 <= index && index <= pat.length && index <= a.length;
//@ maintaining (\forall int i; 0 <= i && i < index; pat[i] == a[i]);
//@ decreases pat.length - index;
while((pat.length > index) && (a.length > index))
{
if(pat[index] == a[index]){
index = index + 1;
} else {
return index;
}
}
return index;
}
}