c# override用法

要擴展或修改繼承的方法、屬性、索引器或事件的抽象實現或虛實現,必須使用 override 修飾符。編程

在此例中,類 Square 必須提供 Area 的重寫實現,由於 Area 是從抽象的 ShapesClass 繼承而來的。ide

abstract class ShapesClass
{
    abstract public int Area();
}
this

class Square : ShapesClass
{
    int x, y;
    // Because ShapesClass.Area is abstract, failing to override
    // the Area method would result in a compilation error.
    public override int Area()
    {
        return x * y;
    }
}
有關 override 關鍵字用法的更多信息,請參見使用 Override 和 New 關鍵字進行版本控制以及瞭解什麼時候使用 Override 和 New 關鍵字。
spa

備註override 方法提供從基類繼承的成員的新實現。經過 override 聲明重寫的方法稱爲重寫基方法。重寫的基方法必須與 override 方法具備相同的簽名。有關繼承的信息,請參見繼承。設計

不能重寫非虛方法或靜態方法。重寫的基方法必須是 virtual、abstract 或 override 的。版本控制

override 聲明不能更改 virtual 方法的可訪問性。override 方法和 virtual 方法必須具備相同的訪問級別修飾符。對象

不能使用修飾符 new、static、virtual 或 abstract 來修改 override 方法。繼承

重寫屬性聲明必須指定與繼承屬性徹底相同的訪問修飾符、類型和名稱,而且被重寫的屬性必須是 virtual、abstract 或 override 的。
示例此示例定義了一個名爲 Employee 的基類,和一個名爲 SalesEmployee 的派生類。SalesEmployee 類包括一個額外的屬性 salesbonus,並重寫方法 CalculatePay 以便將該屬性考慮在內。
索引

using System;
class TestOverride
{
    public class Employee
    {
        public string name;
事件

        // Basepay is defined as protected, so that it may be 
        // accessed only by this class and derrived classes.
        protected decimal basepay;

        // Constructor to set the name and basepay values.
        public Employee(string name, decimal basepay)
        {
            this.name = name;
            this.basepay = basepay;
        }

        // Declared virtual so it can be overridden.
        public virtual decimal CalculatePay()
        {
            return basepay;
        }
    }

    // Derive a new class from Employee.
    public class SalesEmployee : Employee
    {
        // New field that will affect the base pay.
        private decimal salesbonus;

        // The constructor calls the base-class version, and
        // initializes the salesbonus field.
        public SalesEmployee(string name, decimal basepay, 
                  decimal salesbonus) : base(name, basepay)
        {
            this.salesbonus = salesbonus;
        }

        // Override the CalculatePay method 
        // to take bonus into account.
        public override decimal CalculatePay()
        {
            return basepay + salesbonus;
        }
    }

    static void Main()
    {
        // Create some new employees.
        SalesEmployee employee1 = new SalesEmployee("Alice", 
                      1000, 500);
        Employee employee2 = new Employee("Bob", 1200);

        Console.WriteLine("Employee " + employee1.name + 
                  " earned: " + employee1.CalculatePay());
        Console.WriteLine("Employee " + employee2.name + 
                  " earned: " + employee2.CalculatePay());
    }
}
輸出
Employee Alice earned: 1500
Employee Bob earned: 1200
使用 Override 和 New 關鍵字進行版本控制(C# 編程指南) C# 語言通過專門設計,以便不一樣庫中的基類與派生類之間的版本控制能夠不斷向前發展,同時保持向後兼容。這具備多方面的意義。例如,這意味着在基類中引入與派生類中的某個成員具備相同名稱的新成員在 C# 中是徹底支持的,不會致使意外行爲。它還意味着類必須顯式聲明某方法是要重寫一個繼承方法,仍是一個僅隱藏具備相似名稱的繼承方法的新方法。C# 容許派生類包含與基類方法名稱相同的方法。基類方法必須定義爲 virtual。若是派生類中的方法前面沒有 new 或 override 關鍵字,則編譯器將發出警告,該方法將有如存在 new 關鍵字同樣執行操做。若是派生類中的方法前面帶有 new 關鍵字,則該方法被定義爲獨立於基類中的方法。若是派生類中的方法前面帶有 override 關鍵字,則派生類的對象將調用該方法,而不調用基類方法。能夠從派生類中使用 base 關鍵字調用基類方法。override、virtual 和 new 關鍵字還能夠用於屬性、索引器和事件中。默認狀況下,C# 方法不是虛方法 -- 若是將一種方法聲明爲虛方法,則繼承該方法的任何類均可以實現其本身的版本。若要使方法成爲虛方法,必須在基類的方法聲明中使用 virtual 修飾符。而後,派生類可使用 override 關鍵字重寫基虛方法,或使用 new 關鍵字隱藏基類中的虛方法。若是 override 關鍵字和 new 關鍵字均未指定,編譯器將發出警告,而且派生類中的方法將隱藏基類中的方法。有關更多信息,請參見編譯器警告 CS0108。爲了在實踐中演示上述狀況,咱們暫時假定公司 A 建立了一個名爲 GraphicsClass 的類,您的程序使用該類。GraphicsClass 相似以下:C#class GraphicsClass
{
    public virtual void DrawLine() { }
    public virtual void DrawPoint() { }
}

您的公司使用此類,而且您在添加新方法時將其用來派生本身的類:


C#

class YourDerivedGraphicsClass : GraphicsClass
{
    public void DrawRectangle() { }
}

您在應用程序的使用過程當中沒有遇到任何問題,直到公司 A 發佈了 GraphicsClass 的新版本,該新版本相似以下:


C#

class GraphicsClass
{
    public virtual void DrawLine() { }
    public virtual void DrawPoint() { }
    public virtual void DrawRectangle() { }
}

如今,GraphicsClass 的新版本中包含了一個稱爲 DrawRectangle 的方法。最初,一切正常。新版本仍與舊版本二進制兼容 -- 即便在計算機系統中安裝新類,部署的全部軟件仍將繼續工做。在您的派生類中,對方法 DrawRectangle 的任何現有調用將繼續引用您的版本。
可是,一旦使用 GraphicsClass 的新版本從新編譯應用程序,您將收到來自編譯器的警告。有關更多信息,請參見編譯器警告 CS0108。
此警告提示您須要考慮您的 DrawRectangle 方法在應用程序中的工做方式。
若是想用您的方法重寫新的基類方法,請使用 override 關鍵字,以下所示:


C#

class YourDerivedGraphicsClass : GraphicsClass
{
    public override void DrawRectangle() { }
}

override 關鍵字可確保派生自 YourDerivedGraphicsClass 的任何對象都將使用 DrawRectangle 的派生類版本。派生自 YourDerivedGraphicsClass 的對象仍可使用 base 關鍵字訪問 DrawRectangle 的基類版本,以下所示:


C#

base.DrawRectangle();

若是不想用您的方法重寫新的基類方法,則應注意下面的事項。爲避免在兩種方法之間引發混淆,能夠重命名您的方法。重命名方法可能很耗時且容易出錯,並且在某些狀況下並不實用。可是,若是您的項目相對較小,則可使用 Visual Studio 的重構選項來重命名方法。有關更多信息,請參見重構類和類型。
或者,也能夠經過在派生類定義中使用關鍵字 new 來防止出現該警告,以下所示:


C#

class YourDerivedGraphicsClass : GraphicsClass
{
    public new void DrawRectangle() { }
}

使用 new 關鍵字告訴編譯器您的定義將隱藏基類中包含的定義。這是默認行爲。
重寫和方法選擇

當在類中指定方法時,若是有多個方法與調用兼容(例如,存在兩種同名的方法,而且其參數與傳遞的參數兼容),則 C# 編譯器將選擇最佳方法進行調用。下面的方法將是兼容的:


C#

public class Derived : Base
{
    public override void DoWork(int param) { }
    public void DoWork(double param) { }
}

在 Derived 的一個實例中調用 DoWork 時,C# 編譯器將首先嚐試使該調用與最初在 Derived 上聲明的 DoWork 版本兼容。重寫方法不被視爲是在類上進行聲明的,而是在基類上聲明的方法的新實現。僅當 C# 編譯器沒法將方法調用與 Derived 上的原始方法匹配時,它才嘗試將該調用與具備相同名稱和兼容參數的重寫方法匹配。例如:


C#

int val = 5;
Derived d = new Derived();
d.DoWork(val); // Calls DoWork(double).

因爲變量 val 能夠隱式轉換爲 double 類型,所以 C# 編譯器將調用 DoWork(double),而不是 DoWork(int)。有兩種方法能夠避免此狀況。首先,避免將新方法聲明爲與虛方法同名。其次,能夠經過將 Derived 的實例強制轉換爲 Base 來使 C# 編譯器搜索基類方法列表,從而使其調用虛方法。因爲是虛方法,所以將調用 Derived 上的 DoWork(int) 的實現。例如:


C#

((Base)d).DoWork(val); // Calls DoWork(int) on Derived.

相關文章
相關標籤/搜索