代码契约:抽象的不变量 class
Code Contracts: Invariants in abstract class
我在将不变量与代码契约一起使用时遇到了问题。
我想在我的抽象 class 中定义一个不变量,但它被忽略了。下面的代码显示了我的界面和摘要 class.
[ContractClass(typeof(IPointContract))]
interface IPoint
{
int X { get; }
int Y { get; }
}
[ContractClassFor(typeof(IPoint))]
abstract class IPointContract : IPoint
{
public int X
{
get { return 0; }
}
public int Y
{
get { return 0; }
}
[ContractInvariantMethod]
private void PointInvariant()
{
Contract.Invariant(X > Y);
}
}
之后,我在我的 Point class 中实现了这个接口,并从中创建了一个对象。这至少应该在运行时失败。
class Point : IPoint
{
public Point(int X, int Y)
{
this._x = X;
this._y = Y;
}
private int _x;
public int X
{
get { return _x; }
}
private int _y;
public int Y
{
get { return _y; }
}
}
class Program
{
static void Main(string[] args)
{
Point p = new Point(1, 2);
}
}
当我将不变量移动到 Point-Class 时,它工作正常。所有其他前置或 post 条件也都工作正常。
是否不可能在抽象中包含不变量 class 还是我做错了?
接口不支持不变量。 (您的问题标题是"Invariants in abstract class",但问题的症结在于界面。)
我猜这是因为不变量需要状态而接口没有状态。我相信代码合同团队可以解决这个问题,我希望他们能这样做,因为这将是一个很棒的功能。
要解决此限制,您可以:
- 将不变方法添加到派生的 classes(
class Point
等)。
- 或者,将 setter 添加到抽象 class 属性并在 setter 中实现合约逻辑。
我在将不变量与代码契约一起使用时遇到了问题。 我想在我的抽象 class 中定义一个不变量,但它被忽略了。下面的代码显示了我的界面和摘要 class.
[ContractClass(typeof(IPointContract))]
interface IPoint
{
int X { get; }
int Y { get; }
}
[ContractClassFor(typeof(IPoint))]
abstract class IPointContract : IPoint
{
public int X
{
get { return 0; }
}
public int Y
{
get { return 0; }
}
[ContractInvariantMethod]
private void PointInvariant()
{
Contract.Invariant(X > Y);
}
}
之后,我在我的 Point class 中实现了这个接口,并从中创建了一个对象。这至少应该在运行时失败。
class Point : IPoint
{
public Point(int X, int Y)
{
this._x = X;
this._y = Y;
}
private int _x;
public int X
{
get { return _x; }
}
private int _y;
public int Y
{
get { return _y; }
}
}
class Program
{
static void Main(string[] args)
{
Point p = new Point(1, 2);
}
}
当我将不变量移动到 Point-Class 时,它工作正常。所有其他前置或 post 条件也都工作正常。
是否不可能在抽象中包含不变量 class 还是我做错了?
接口不支持不变量。 (您的问题标题是"Invariants in abstract class",但问题的症结在于界面。)
我猜这是因为不变量需要状态而接口没有状态。我相信代码合同团队可以解决这个问题,我希望他们能这样做,因为这将是一个很棒的功能。
要解决此限制,您可以:
- 将不变方法添加到派生的 classes(
class Point
等)。 - 或者,将 setter 添加到抽象 class 属性并在 setter 中实现合约逻辑。