C#继承最佳实践

C#继承最佳实践,c#,inheritance,C#,Inheritance,我有一个名为BaseView的普通类,它有一个虚拟方法DisplayView。此方法调用GetHeader和GetBody虚拟方法来获取页面内容。然后,我将创建一个继承自BaseView的类,并重写需要以不同于基类的方式显示内容的方法 我的问题是,尽管这很有效,但在运行代码分析时,会警告我不要直接调用虚拟函数 我是否应该在基类之上创建另一个类层,覆盖虚拟函数并仅从该基类继承 直接使用虚拟方法的缺点是什么 编辑:警告是: CA2214:Microsoft。用法:xxx包含导致 调用该类定义的虚拟方

我有一个名为
BaseView
的普通类,它有一个虚拟方法
DisplayView
。此方法调用
GetHeader
GetBody
虚拟方法来获取页面内容。然后,我将创建一个继承自
BaseView
的类,并重写需要以不同于基类的方式显示内容的方法

我的问题是,尽管这很有效,但在运行代码分析时,会警告我不要直接调用虚拟函数

我是否应该在基类之上创建另一个类层,覆盖虚拟函数并仅从该基类继承

直接使用虚拟方法的缺点是什么

编辑:警告是:

CA2214:Microsoft。用法:xxx包含导致 调用该类定义的虚拟方法。回顾以下内容 意外后果的调用堆栈


我认为问题在于
DisplayView
是虚拟的,它调用虚拟方法。在大多数情况下,虚拟方法被final方法调用,作为改变行为的一种手段,例如在策略模式中。如果最后一个方法调用虚拟方法,编译器知道虚拟方法将始终在所有派生类中被调用,因此虚拟方法的存在是有效的

事实上,您从虚拟调用虚拟意味着您的设计可能会受到质疑:如果
DisplayView
是虚拟的,另一个实现可能会覆盖它。当前实现调用虚拟
GetHeader
,但派生类可能不调用。因此,它不能保证
GetHeader
不是死代码

这可能就是FxCop吸引您注意的地方。它想知道,如果您在基类中定义了一个虚拟方法(
GetHeader
),那么所有派生实现都将使用它


我会把重点放在最终的显示视图上,或者从这个角度来评估你的设计。

请在派生类方法实现中显示确切的警告消息add new/override关键字,这个警告可能会出现。如果你从构造函数调用你的虚方法,检查这个问题:@Maheep使用new关键字不会覆盖基类方法,而是简单地隐藏基类实现代码分析消息编号是什么(应该称为CA2214或类似名称)?我花了很长时间使用FxCop,规则中有一些非常有趣的想法,其中大部分我都勉强同意!但是,声明说,如果不是从构造函数中调用虚方法,那么应该可以,或者至少我从这个有趣的例子中了解到了这一点。问题没有提到这是从构造函数调用的。是吗?是的,OP提到他正在从另一个虚拟方法调用虚拟方法
GetHeader
GetBody
,所以我不明白这个规则在这里是如何应用的。预期的行为是虚拟GetHeader方法可能返回一个包含视图名称的简单字符串。在某些情况下,可能需要更复杂的头,然后派生类将重写GetHeader。虚拟方法DisplayView(从派生类调用)随后将调用GetHeader的重写方法。