Geo*_*kov 71 c# java methods virtual-functions
在Java中,您可以将方法标记为final,以使其无法覆盖.
在C#中,您必须将方法标记为虚拟,以便可以覆盖.
这是否意味着在C#中你应该将所有方法标记为虚拟(除了一些你不想被覆盖的方法),因为很可能你不知道你的类可以以什么方式被继承?
Eri*_*ert 137
在C#中,您必须将方法标记为虚拟,以便可以覆盖.这是否意味着在C#中你应该将所有方法标记为虚拟(除了一些你不想被覆盖的方法),因为很可能你不知道你的类可以以什么方式被继承?
不.如果语言设计者认为虚拟应该是默认值,那么它将是默认值.
Overridablility是一项功能,与所有功能一样,它具有成本.可重复方法的成本相当可观:设计,实施和测试成本很高,特别是如果对课程有任何"敏感性"; 虚方法是将未经测试的第三方代码引入系统并具有安全影响的方法.
如果您不知道如何继承您的课程,那么请不要发布您的课程,因为您还没有完成设计.您的可扩展性模型绝对是您应该提前知道的; 它应该深刻影响你的设计和测试策略.
我主张所有类都是密封的,所有方法都是非虚拟的,直到你有一个真实的,以客户为中心的理由来开启或使方法成为虚拟.
基本上你的问题是"我不知道我的客户打算如何消费我的课程;我是否应该让它任意扩展?" 没有; 你应该变得知识渊博!你不会问"我不知道我的客户将如何使用我的类,所以我应该把我的所有属性都读写吗?我应该让我的所有方法读写代理类型的属性,以便我的用户可以用自己的实现替换任何方法吗?" 不,在您有证据表明用户确实需要该功能之前,请不要执行任何操作!花费宝贵的时间设计,测试和实现用户真正想要和需要的功能,并从知识的位置进行.
Pat*_*lug 26
在我看来,目前接受的答案是不必要的教条.
事实是,当你没有将方法标记为virtual,其他人不能覆盖它的行为,当你标记一个类时,sealed其他人不能从类继承.这可能会导致严重的疼痛.我不知道有多少次我诅咒API标记类sealed或不标记方法virtual只是因为他们没有预料到我的用例.
从理论上讲,它可能是一种正确的方法,只允许重写方法和继承那些意图被覆盖和继承的类,但在实践中,不可能预见到每一种可能的情况,并且确实没有充分理由这么封闭.
sealed.virtual.进行调用的一种方法是查看方法或属性的名称.一对GetLength()在列表的方法不正是顾名思义,它不允许太多的解释.改变其实施可能不是非常透明,因此标记它virtual可能是不必要的.将Add方法标记为虚拟更有用,因为有人可以创建一个特殊的List,它只通过Add方法等接受一些对象.另一个例子是自定义控件.您可能希望制作主绘图方法,virtual以便其他人可以使用大部分行为并只更改外观,但您可能不会覆盖X和Y属性.
最后,您通常不必立即做出决定.在一个内部项目中,您可以轻松地更改代码,我不会担心这些事情.如果需要覆盖某个方法,则可以在发生这种情况时将其设置为虚拟.相反,如果项目是由其他人使用并且更新缓慢的API或库,那么考虑哪些类和方法可能有用肯定是值得的.在这种情况下,我认为开放而不是严格关闭更好.
不可以.只有您希望派生类指定的方法才应该是虚拟的.
虚拟与最终无关.
要防止覆盖c#中的虚拟方法,请使用 sealed
public class MyClass
{
public sealed override void MyFinalMethod() {...}
}
Run Code Online (Sandbox Code Playgroud)