c#-4.0 – 为什么我不能以覆盖的方法添加Contract.Requires?

我正在使用代码合同(实际上,学习使用这个).

我正在面对一些奇怪的东西,我覆盖了一个在第三方大会定义的方法.我想添加一个Contract.Require语句,如下所示:

public class MyClass: MyParentClass
{
    protected override void DoIt(MyParameter param)
    {
        Contract.Requires<ArgumentNullException>(param != null);

        this.ExecuteMyTask(param.something);
    }

    protected void ExecuteMyTask(MyParameter param)
    {
        Contract.Requires<ArgumentNullException>(param != null);
        /* body of the method */
    }
}

但是,我收到如下警告:

Warning 1 CodeContracts:
Method ‘MyClass.DoIt(MyParameter)’ overrides ‘MyParentClass.DoIt(MyParameter))’,thus cannot add Requires.

[编辑]更改代码一点显示替代问题[/编辑]

如果我在DoIt方法删除了Contract.Requires,我会收到另一个警告,告诉我我必须提供未经证实的param!= null
我不明白这个警告.是什么原因,我可以解决吗?

解决方法

您不能添加您的呼叫者可能不知道的额外要求.它违反了 Liskov’s Subtitution Principle.多态的观点是,一个调用者应该能够将一个引用实际引用到派生类的一个实例,就像它引用基类的一个实例一样.

考虑:

MyParentClass foo = GetParentClassFromSomewhere();
DoIt(null);

如果这是静态确定为有效的,您的派生类可以握住它是错误的,并说“不,你不打算用空论调用DoIt!”合同静态分析的目的是,您可以在编译时确定调用,逻辑等的有效性,因此在执行时不需要添加额外的限制,这是由于多态而发生的.

派生类可以添加关于它将做什么的保证 – 它将确保什么 – 但是它不能再提供来自其重载方法的呼叫者的更多要求.

相关文章

原文地址:http://msdn.microsoft.com/en-us/magazine/cc163...
前言 随着近些年微服务的流行,有越来越多的开发者和团队所采...
最近因为比较忙,好久没有写博客了,这篇主要给大家分享一下...
在多核CPU在今天和不久的将来,计算机将拥有更多的内核,Mic...
c语言输入成绩怎么判断等级
字符型数据在内存中的存储形式是什么