如何在 C# 中禁止重写类方法/属性?

发布于 2024-11-18 16:56:53 字数 90 浏览 5 评论 0原文

我相信我希望类的某些方法和属性是不可重写的,并在所有派生类中使用基类的实现。如何实现这一目标? seal 关键字似乎不起作用,并表示“无法密封方法,因为它不是覆盖”。

I believe I want a some methods and properties of a class to be unoverridable and use the base's implementation in all derived classes. How to achieve this? sealed keyword doesn't seem to work and says "method can not be sealed because it is not an override".

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

强辩 2024-11-25 16:56:54

尚未被重写的方法将不可被重写,除非您将其标记为virtual。所以听起来你的情况不需要采取任何行动。

class A
{
    public void B() {} // can't override
    public virtual C() {} // can override
    public virtual D() {} // can override
}

sealed 修饰符仅在方法已经覆盖基类中的成员时才适用。这允许您防止覆盖该类的子类。

class A1 : A
{
    public void B() {} // shadows A.B.  Not a virtual method!
    public override C() {} // overrides A.C, subclasses can override
    public override sealed D() {} // overrides A.D, subclasses cannot override
                                  // (but can shadow)
}

A method that is not already an override will not be overridable unless you mark it as virtual. So it sounds like in your case no action is needed.

class A
{
    public void B() {} // can't override
    public virtual C() {} // can override
    public virtual D() {} // can override
}

The sealed modifier only applies when a method is already an override of a member in the base class. This allows you to prevent overrides in subclasses of that class.

class A1 : A
{
    public void B() {} // shadows A.B.  Not a virtual method!
    public override C() {} // overrides A.C, subclasses can override
    public override sealed D() {} // overrides A.D, subclasses cannot override
                                  // (but can shadow)
}
娇纵 2024-11-25 16:56:54

这是不可能的。派生类始终可以使用 new 关键字隐藏(而不是重写)其父类方法。 seal 关键字只是阻止派生类重写虚拟方法,但它仍然可以使用 new 来隐藏基方法。

This isn't possible. A derived class can always use the new keyword to hide (not override) its parents methods. The sealed keyword simply stops the derived class from overriding a virtual method, but it could still use new to hide the base method.

揽清风入怀 2024-11-25 16:56:54

仅当您重写虚拟方法,但不希望从您的实现派生的类再次重写它时,才能使用“sealed”关键字。您所需要的只是声明该方法不是虚拟的。

正如其他人指出的那样,实际上有一个“new”关键字,它允许隐藏该方法。但是只要您使用基类的引用,您的基方法总是会被调用:

class BaseClass
{
     public void Foo() { Console.WriteLine("Foo"); }
}

class Derived : BaseClass
{
     public new void Foo() { Console.WriteLine("Bar"); }
}

public static void Main()
{
     Derived derived = new Derived();
     derived.Foo(); // Prints "Bar"
     BaseClass baseClass = derived;
     baseClass.Foo(); // Prints "Foo"
}

因为只有提供基类才有意义,只要您在任何地方使用“BaseClass”指针,您的方法就无法被隐藏。

The "sealed" keyword can only be used, if you override a method that is virtual, but don't want a class deriving from your implementation to override it again. Declaring the method not virtual is all you need.

As other pointed out that there is in fact a "new" keyword, which allows hiding the method. But as long as you use a reference of your base class, your base method is always called:

class BaseClass
{
     public void Foo() { Console.WriteLine("Foo"); }
}

class Derived : BaseClass
{
     public new void Foo() { Console.WriteLine("Bar"); }
}

public static void Main()
{
     Derived derived = new Derived();
     derived.Foo(); // Prints "Bar"
     BaseClass baseClass = derived;
     baseClass.Foo(); // Prints "Foo"
}

Since providing a base-class only makes sense, as long as you use a "BaseClass"-pointer everywhere, your method cannot be hidden.

她比我温柔 2024-11-25 16:56:54

这正是 sealed 关键字的用途。

http://msdn.microsoft.com/en-us/library/ms173150.aspx

类成员、方法、字段、
派生类的属性或事件
这是覆盖虚拟成员
基类可以声明该成员
密封的。这否定了虚拟
会员的任何进一步方面
派生类。这是通过以下方式完成的
将密封关键字放在前面
override 类成员中的关键字
声明。

如果您重写了基类中的方法,请使用sealed
如果您已在类中声明了一个方法,并且不希望在任何派生类中重写该方法,则不要将其标记为虚拟。只有虚拟成员可以被覆盖。

This is precisely what sealed keyword is for.

http://msdn.microsoft.com/en-us/library/ms173150.aspx

A class member, method, field,
property, or event, on a derived class
that is overriding a virtual member of
the base class can declare that member
as sealed. This negates the virtual
aspect of the member for any further
derived class. This is accomplished by
putting the sealed keyword before the
override keyword in the class member
declaration.

If you've overridden a method from base class than use sealed.
If you've declared a method in the class and don't want it to be overridden in any derived classes than don't mark it as virtual. Only virtual members can be overridden.

白衬杉格子梦 2024-11-25 16:56:53

默认情况下,C# 中的成员是密封的 - 除非将它们标记为虚拟,否则无论如何都不能在派生类中重写它们。

诚然,它们可以在派生类中隐藏

public new void SomeMethod()
{
}

...但这与重写不同。您无法阻止这种情况,但如果调用者使用基类的编译时类型,他们最终不会意外地调用它。

如果您可以向我们提供更多关于您想要阻止的内容(来自调用者的 POV 和被调用的代码)的详细信息,我们也许能够提供更多帮助。

Members are sealed by default in C# - unless they're marked as virtual, they can't be overridden in derived classes anyway.

They can be shadowed in derived classes, admittedly:

public new void SomeMethod()
{
}

... but that's not the same as overriding. There's no way you can prevent this, but if a caller uses a compile-time type of the base class, they won't end up calling this accidentally anyway.

If you could give us more details of exactly what you're trying to prevent (from both the caller's POV and the code being called) we may be able to help more.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文