簡體   English   中英

如何覆蓋常量派生類?

[英]How to override constants derived classes?

代碼 :

public class A {
    public const int beingSupportedRate = 0;
}

 public partial class B : A {
    public const int beingSupportedRate = 1;

}

由於性能,我希望它像 const int 一樣明確。 將 virtual 放在class A變量beingSupportedRate會導致編譯器錯誤如下:

The modifier 'virtual' is not valid for this item

您應該使用new關鍵字顯式隱藏繼承的成員:

public class A
{
    public const int beingSupportedRate = 0;
}

public class B : A
{
    public new const int beingSupportedRate = 1;
}

請記住,您無法從實例訪問常量成員。

Console.WriteLine(A.beingSupportedRate);
Console.WriteLine(B.beingSupportedRate);

輸出:

0
1

使用此解決方案時,您應該考慮一些問題。 以下面的控制台程序為例:

class Program
{
    static void Main(string[] args)
    {
        A a = new A();
        B b = new B();
        C c = new C();

        a.GetBeingSupportRate();
        b.GetBeingSupportRate();
        c.GetBeingSupportRate();

        Console.Read();
    }

    public class A
    {
        public const int beingSupportedRate = 0;
        public void GetBeingSupportRate()
        {
            Console.WriteLine(beingSupportedRate);
        }
    }

    public class B : A
    {
        public new const int beingSupportedRate = 1;

    }

    public class C : B
    {

    }
}

這將為所有三個類實例輸出0 ,因為繼承的方法使用 A 中的常量值。這意味着您必須覆蓋引用該常量的所有方法。

首選方法是使用具有必須實現的屬性的接口,而不是為此目的使用常量。

字段(包括常量)不能是虛擬的。 這與它是一個常量無關......這只是字段的工作方式......盡管常量隱式靜態的事實使它不可行,就像它一樣。

如果你想多態行為,它必須通過一個實例成員是一個屬性,方法或事件。

順便說一句,我強烈懷疑您的“出於性能原因,我希望將其作為const ”的理由是虛假的微優化。 甚至不清楚您是如何使用它的,但我非常懷疑您是否已將其作為非常數進行嘗試並證明它太慢了。

常量不能被覆蓋,它們是常量。

如果您希望這個值可以通過擴展來改變,那么您需要使用不那么常量的東西,具有根據上下文更改的性質,例如要實現的abstract元素或要覆蓋的virtual元素。

其實我相信你誤解了面向對象編程中的多態性。

常量、字段和變量只是一個存儲(好吧,引用,但我是從概念的角度討論的)。

多態是關於改變某物的行為。 覆蓋常量不能改變行為,而是改變它的值

另一點是常量是static ,因此它不屬於實例,但AppDomain有一個不可變的單個值,並且它在應用程序生命周期中存活。

有了上面的語句,為什么要像實例成員一樣覆蓋常量? 你能想象接下來的情況嗎?

public class A 
{
      public virtual const int Some = 1;
}

public class B : A
{
      public override const int Some = 2;
}

public class C : A
{
     // No override here!
}

int valueOfSomeConstant = C.Some;

抓住! 如果常量是靜態的,即使C沒有覆蓋任何常量, C.Some也會是2

從你的問題中引用一些:

由於性能,我希望它像 const int 一樣明確。 [...]

這只有一個答案:過早的優化是任何軟件開發的魔鬼。

正如 Jon Skeet 所說,這將是您最不關心的問題。

你可以做到這一點,我猜:

public class A 
{
    public virtual Int32 beingSupportedRate
    { 
        get { return 0; }
    }
}

public class B : A
{
    public override Int32 beingSupportedRate 
    {
        get { return 1; }
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM