Assume the following code:
[ContractClass(typeof(ICC4Contract))]
public interface ICC4
{
bool IsFooSet { get; }
string Foo { get; }
}
public class CC4 : ICC4
{
private string _foo;
public bool IsFooSet { get { return Foo != null; } }
public string Foo { get { return _foo; } }
}
[ContractClassFor(typeof(ICC4))]
public abstract class ICC4Contract : ICC4
{
public bool IsFooSet
{
get
{
Contract.Ensures((Contract.Result<bool>() && Foo != null)
|| !Contract.Result<bool>());
return false;
}
}
public string Foo
{
get
{
Contract.Ensures((Contract.Result<string>() != null && IsFooSet)
|| !IsFooSet);
return null;
}
}
}
The contracts try to say:
IsFooSet will return true if Foo is not null.Foo doesn't return null if IsFooSet returns true.This almost works.
However, I get an "ensures unproven" on return _foo;, because the checker doesn't realize that Foo will always equal _foo.
Changing Foo to an automatic property with a private setter removes that warning, but I don't want to do that (I don't like automatic properties with private setters).
What do I have to change in the above code to make the warning go away while preserving the _foo field?
The following doesn't work:
IsFooSet to use _foo instead of Foo. It will result in an additional "ensures unproven" on IsFooSet.Foo == _foo. This will result in an "invariant unproven" on the implicit, default constructor. Furthermore, on a real code-base the processing time of the static checker will be magnitudes higher.Contract.Ensures(Contract.Result<string>() == _foo); to the getter of Foo as per this answer doesn't change anything.You can use short-circuiting to simplify the condition, and that works for some reason:
[ContractClassFor(typeof(ICC4))]
public abstract class ICC4Contract : ICC4
{
public bool IsFooSet
{
get
{
Contract.Ensures(!Contract.Result<bool>() || Foo != null);
return false;
}
}
public string Foo
{
get
{
Contract.Ensures(!IsFooSet || Contract.Result<string>() != null);
return null;
}
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With