<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ??碼云GVP開源項目 12k star Uniapp+ElementUI 功能強大 支持多語言、二開方便! 廣告
                # C# 中的方法 > 原文: [https://zetcode.com/lang/csharp/methods/](https://zetcode.com/lang/csharp/methods/) 在本教程的這一部分中,我們將介紹 C# 方法。 在面向對象的編程中,我們使用對象。 對象是程序的基本構建塊。 對象由數據和方法組成。 方法更改創建的對象的狀態。 它們是對象的動態部分。 數據是靜態部分。 ## C# 方法定義 方法是包含一系列語句的代碼塊。 方法必須在類或結構中聲明。 好的編程習慣是方法僅執行一項特定任務。 方法為程序帶來了模塊化。 正確使用方法具有以下優點: * 減少代碼重復 * 將復雜的問題分解成更簡單的部分 * 提高代碼的清晰度 * 重用代碼 * 信息隱藏 ## C# 方法特征 方法的基本特征是: * 訪問權限 * 返回值類型 * 方法名稱 * 方法參數 * 括號 * 語句塊 方法的訪問級別由訪問修飾符控制。 他們設置方法的可見性。 他們確定誰可以調用該方法。 方法可以將值返回給調用方。 如果我們的方法返回一個值,我們將提供其數據類型。 如果不是,則使用`void`關鍵字指示我們的方法不返回值。 方法參數用括號括起來,并用逗號分隔。 空括號表示該方法不需要任何參數。 方法塊周圍包含{}個字符。 當方法被調用時,該塊包含一個或多個執行的語句。 擁有一個空的方法塊是合法的。 ## C# 方法簽名 方法簽名是 C# 編譯器方法的唯一標識。 簽名由方法名稱以及其每個形式參數的類型和種類(值,引用或輸出)組成。 方法簽名不包括返回類型。 可以在方法名稱中使用任何合法字符。 按照約定,方法名稱以大寫字母開頭。 方法名稱是動詞或動詞,后跟形容詞或名詞。 隨后的每個單詞都以大寫字母開頭。 以下是 C# 中方法的典型名稱: * `Execute` * `FindId` * `SetName` * `GetName` * `CheckIfValid` * `TestValidity` ## C# 簡單示例 我們從一個簡單的例子開始。 `Program.cs` ```cs using System; namespace SimpleMethod { class Base { public void ShowInfo() { Console.WriteLine("This is Base class"); } } class Program { static void Main(string[] args) { Base bs = new Base(); bs.ShowInfo(); } } } ``` 我們有一個`ShowInfo()`方法,它打印其類的名稱。 ```cs class Base { public void ShowInfo() { Console.WriteLine("This is Base class"); } } ``` 每個方法都必須在類或結構內定義。 它必須有一個名字。 在我們的情況下,名稱為`ShowInfo()`。 方法名稱之前的關鍵字是訪問說明符和返回類型。 括號跟隨方法的名稱。 它們可能包含方法的參數。 我們的方法沒有任何參數。 ```cs static void Main() { ... } ``` 這是`Main()`方法。 它是每個控制臺或 GUI 應用的入口點。 必須聲明為`static`。 我們將在后面看到原因。 `Main()`方法的返回類型可以是`void`或`int`。 省略了`Main()`方法的訪問說明符。 在這種情況下,將使用默認值`private`。 不建議對`Main()`方法使用`public`訪問說明符。 程序集中的任何其他方法都不應調用它。 當應用啟動時,只有 CLR 才能調用它。 ```cs Base bs = new Base(); bs.ShowInfo(); ``` 我們創建`Base`類的實例。 我們在對象上調用`ShowInfo()`方法。 我們說該方法是一個實例方法,因為它需要一個實例來調用。 通過指定對象實例,成員訪問運算符(點),方法名稱,來調用該方法。 ## C# 方法參數 參數是傳遞給方法的值。 方法可以采用一個或多個參數。 如果方法使用數據,則必須將數據傳遞給方法。 我們通過在括號內指定它們來實現。 在方法定義中,我們必須為每個參數提供名稱和類型。 `Program.cs` ```cs using System; namespace MethodParameters { class Addition { public int AddTwoValues(int x, int y) { return x + y; } public int AddThreeValues(int x, int y, int z) { return x + y + z; } } class Program { static void Main(string[] args) { Addition a = new Addition(); int x = a.AddTwoValues(12, 13); int y = a.AddThreeValues(12, 13, 14); Console.WriteLine(x); Console.WriteLine(y); } } } ``` 在上面的示例中,我們有兩種方法。 其中一個帶有兩個參數,另一個帶有三個參數。 ```cs public int AddTwoValues(int x, int y) { return x + y; } ``` `AddTwoValues()`方法采用兩個參數。 這些參數具有`int`類型。 該方法還向調用者返回一個整數。 我們使用`return`關鍵字從方法中返回一個值。 ```cs public int AddThreeValues(int x, int y, int z) { return x + y + z; } ``` `AddThreeValues()`與先前的方法相似。 它帶有三個參數。 ```cs int x = a.AddTwoValues(12, 13); ``` 我們稱為加法對象的`AddTwoValues()`方法。 它有兩個值。 這些值將傳遞給方法。 該方法返回一個分配給`x`變量的值。 ## C# 變量數量可變 方法可以采用可變數量的參數。 為此,我們使用`params`關鍵字。 `params`關鍵字之后不允許有其他參數。 方法聲明中僅允許使用一個`params`關鍵字。 `Program.cs` ```cs using System; namespace SumOfValues { class Program { static void Main(string[] args) { Sum(1, 2, 3); Sum(1, 2, 3, 4, 5); } static void Sum(params int[] list) { Console.WriteLine("There are {0} items", list.Length); int sum = 0; foreach (int i in list) { sum = sum + i; } Console.WriteLine("Their sum is {0}", sum); } } } ``` 我們創建一個`Sum()`方法,該方法可以使用可變數量的參數。 該方法將計算傳遞給該方法的值的總和。 ```cs Sum(1, 2, 3); Sum(1, 2, 3, 4, 5); ``` 我們兩次調用`Sum()`方法。 在一種情況下,它需要 3 個參數,在第二種情況下,它需要 5 個參數。我們調用相同的方法。 ```cs static void Sum(params int[] list) { ... } ``` `Sum()`方法可以采用可變數量的整數值。 所有值都添加到列表數組中。 ```cs Console.WriteLine("There are {0} items", list.Length); ``` 我們打印列表數組的長度。 ```cs int sum = 0; foreach (int i in list) { sum = sum + i; } ``` 我們計算列表中值的總和。 ```cs $ dotnet run There are 3 items Their sum is 6 There are 5 items Their sum is 15 ``` 這是示例的輸出。 ## C# 返回元組 C# 方法可以使用元組返回多個值。 `Program.cs` ```cs using System; using System.Collections.Generic; using System.Linq; namespace ReturingTuples { class Program { static void Main(string[] args) { var vals = new List<int> { 11, 21, 3, -4, -15, 16, 5 }; (int min, int max, int sum) = BasicStats(vals); Console.WriteLine($"Minimum: {min}, Maximum: {max}, Sum: {sum}"); } static (int, int, int) BasicStats(List<int> vals) { int sum = vals.Sum(); int min = vals.Min(); int max = vals.Max(); return (min, max, sum); } } } ``` 我們有`BasicStats()`方法,該方法返回整數列表的基本統計信息。 ```cs using System.Linq; ``` 我們需要為`Sum()`,`Min()`和`Max()`擴展方法導入`System.Linq`。 ```cs var vals = new List<int> { 11, 21, 3, -4, -15, 16, 5 }; ``` 我們有一個整數值列表。 我們要根據這些值計算一些基本統計數據。 ```cs (int min, int max, int sum) = BasicStats(vals); ``` 我們使用解構操作將元組元素分配給三個變量。 ```cs static (int, int, int) BasicStats(List<int> vals) { ``` 方法聲明指定我們返回一個元組。 ```cs return (min, max, sum); ``` 我們返回三個元素的元組。 ```cs $ dotnet run Minimum: -15, Maximum: 21, Sum: 37 ``` 這是輸出。 ## C# 匿名方法 匿名方法是沒有名稱的內聯方法。 匿名方法消除了創建單獨方法的需要,從而減少了編碼開銷。 如果沒有匿名方法,開發者通常不得不創建一個類來僅調用一個方法。 `Program.cs` ```cs using System; using System.Timers; namespace AnonymousMethod { class Program { static void Main(string[] args) { var timer = new Timer(); timer.Elapsed += new ElapsedEventHandler( delegate(object source, ElapsedEventArgs e) { Console.WriteLine("Event triggered at {0}", e.SignalTime); } ); timer.Interval = 2000; timer.Enabled = true; Console.ReadLine(); } } } ``` 我們創建一個計時器對象,然后每 2 秒調用一個匿名方法。 ```cs var timer = new Timer(); ``` `Timer`類在應用中生成重復事件。 ```cs timer.Elapsed += new ElapsedEventHandler( delegate(object source, ElapsedEventArgs e) { Console.WriteLine("Event triggered at {0}", e.SignalTime); } ); ``` 在這里,我們將匿名方法插入`Elapsed`事件。 `delegate`關鍵字用于表示匿名方法。 ```cs Console.ReadLine(); ``` 此時,程序等待來自用戶的輸入。 當我們按下`Return`鍵時,程序結束。 否則,程序將在事件生成之前立即完成。 ## C# 通過值,通過引用傳遞參數 C# 支持兩種將參數傳遞給方法的方式:按值和按引用。 參數的默認傳遞是按值傳遞。 當我們按值傳遞參數時,該方法僅適用于值的副本。 當我們處理大量數據時,這可能會導致性能開銷。 我們使用`ref`關鍵字通過引用傳遞值。 當我們通過引用傳遞值時,該方法會收到對實際值的引用。 修改后,原始值會受到影響。 這種傳遞值的方式更加節省時間和空間。 另一方面,它更容易出錯。 我們應該使用哪種方式傳遞參數? 這取決于實際情況。 假設我們有一組數據,例如員工工資。 如果我們要計算數據的某些統計信息,則無需修改它們。 我們可以傳遞值。 如果我們處理大量數據,并且計算速度至關重要,則可以引用。 如果我們要修改數據,例如進行一些減薪或加薪,我們可以引用一下。 以下示例顯示了如何通過值傳遞參數。 `Program.cs` ```cs using System; namespace PassingByValues { class Program { static int a = 4; static int b = 7; static void Main(string[] args) { Console.WriteLine("Outside Swap method"); Console.WriteLine("a is {0}", a); Console.WriteLine("b is {0}", b); Swap(a, b); Console.WriteLine("Outside Swap method"); Console.WriteLine("a is {0}", a); Console.WriteLine("b is {0}", b); } static void Swap(int a, int b) { int temp = a; a = b; b = temp; Console.WriteLine("Inside Swap method"); Console.WriteLine("a is {0}", a); Console.WriteLine("b is {0}", b); } } } ``` `Swap()`方法在`a`和`b`變量之間交換數字。 原始變量不受影響。 ```cs static int a = 4; static int b = 7; ``` 最初,這兩個變量被啟動。 變量必須聲明為`static`,因為它們是從靜態方法中使用的。 ```cs Swap(a, b); ``` 我們稱為`Swap()`方法。 該方法將`a`和`b`變量作為參數。 ```cs int temp = a; a = b; b = temp; ``` 在`Swap()`方法內部,我們更改了值。 請注意,`a`和`b`變量是在本地定義的。 它們僅在`Swap()`方法內部有效。 ```cs $ dotnet run Outside Swap method a is 4 b is 7 Inside Swap method a is 7 b is 4 Outside Swap method a is 4 b is 7 ``` 輸出顯示原始變量不受影響。 下一個代碼示例通過引用將值傳遞給方法。 原始變量在`Swap()`方法內更改。 方法定義和方法調用都必須使用`ref`關鍵字。 `Program.cs` ```cs using System; namespace PassingByReference { class Program { static int a = 4; static int b = 7; static void Main(string[] args) { Console.WriteLine("Outside Swap method"); Console.WriteLine("a is {0}", a); Console.WriteLine("b is {0}", b); Swap(ref a, ref b); Console.WriteLine("Outside Swap method"); Console.WriteLine("a is {0}", a); Console.WriteLine("b is {0}", b); } static void Swap(ref int a, ref int b) { int temp = a; a = b; b = temp; Console.WriteLine("Inside Swap method"); Console.WriteLine("a is {0}", a); Console.WriteLine("b is {0}", b); } } } ``` 在此示例中,調用`Swap()`方法將更改原始值。 ```cs Swap(ref a, ref b); ``` 我們用兩個參數調用該方法。 它們前面帶有`ref`關鍵字,指示我們正在通過引用傳遞參數。 ```cs static void Swap(ref int a, ref int b) { ... } ``` 同樣在方法聲明中,我們使用`ref`關鍵字來通知編譯器我們接受對參數而不是值的引用。 ```cs $ dotnet run Outside Swap method a is 4 b is 7 Inside Swap method a is 7 b is 4 Outside Swap method a is 7 b is 4 ``` 在這里,我們看到`Swap()`方法確實改變了變量的值。 `out`關鍵字類似于`ref`關鍵字。 不同之處在于,使用`ref`關鍵字時,必須在傳遞變量之前對其進行初始化。 使用`out`關鍵字,可能無法初始化。 方法定義和方法調用都必須使用`out`關鍵字。 `Program.cs` ```cs using System; namespace OutKeyword { class Program { static void Main(string[] args) { int val; SetValue(out val); Console.WriteLine(val); } static void SetValue(out int i) { i = 12; } } } ``` 一個示例顯示`out`關鍵字的用法。 ```cs int val; SetValue(out val); ``` 聲明了`val`變量,但未初始化。 我們將變量傳遞給`SetValue()`方法。 ```cs static void SetValue(out int i) { i = 12; } ``` 在`SetValue()`方法內部,分配了一個值,該值隨后會打印到控制臺。 ## C# 方法重載 方法重載允許創建多個具有相同名稱的方法,它們的輸入類型彼此不同。 方法重載有什么好處? Qt5 庫提供了一個很好的用法示例。 `QPainter`類具有三種繪制矩形的方法。 它們的名稱為`drawRect()`,其參數不同。 一個引用一個浮點矩形對象,另一個引用一個整數矩形對象,最后一個引用四個參數:`x`,`y`,`width`,`height`。 如果開發 Qt 的 C++ 語言沒有方法重載,則庫的創建者必須將其命名為`drawRectRectF()`,`drawRectRect()`和`drawRectXYWH()`之類的方法。 方法重載的解決方案更為優雅。 `Program.cs` ```cs using System; namespace Overloading { class Sum { public int GetSum() { return 0; } public int GetSum(int x) { return x; } public int GetSum(int x, int y) { return x + y; } } class Program { static void Main() { var s = new Sum(); Console.WriteLine(s.GetSum()); Console.WriteLine(s.GetSum(20)); Console.WriteLine(s.GetSum(20, 30)); } } } ``` 我們有三種方法`GetSum()`。 它們的輸入參數不同。 ```cs public int GetSum(int x) { return x; } ``` 這一個參數。 ```cs Console.WriteLine(s.GetSum()); Console.WriteLine(s.GetSum(20)); Console.WriteLine(s.GetSum(20, 30)); ``` 我們調用這三種方法。 ```cs $ dotnet run 0 20 50 ``` 這就是我們運行示例時得到的。 ## C# 遞歸 在數學和計算機科學中,遞歸是一種定義方法的方法,其中所定義的方法在其自己的定義內應用。 換句話說,遞歸方法會調用自身來完成其工作。 遞歸是解決許多編程任務的一種廣泛使用的方法。 一個典型的例子是階乘的計算。 `Program.cs` ```cs using System; namespace Recursion { class Program { static void Main(string[] args) { Console.WriteLine(Factorial(6)); Console.WriteLine(Factorial(10)); } static int Factorial(int n) { if (n == 0) { return 1; } else { return n * Factorial(n-1); } } } } ``` 在此代碼示例中,我們計算兩個數字的階乘。 ```cs return n * Factorial(n-1); ``` 在階乘方法的主體內部,我們將階乘方法稱為經過修改的參數。 該函數調用自身。 ```cs $ dotnet run 720 3628800 ``` 這些就是結果。 ## C# 方法作用域 在方法內部聲明的變量具有方法作用域。 名稱的作用域是程序文本的區域,在該區域內,可以引用由名稱聲明的實體而無需使用名稱限定。 在方法內部聲明的變量具有方法作用域。 它也稱為本地作用域。 該變量僅在此特定方法中有效。 `Program.cs` ```cs using System; namespace MethodScope { class Test { int x = 1; public void exec1() { Console.WriteLine(this.x); Console.WriteLine(x); } public void exec2() { int z = 5; Console.WriteLine(x); Console.WriteLine(z); } } class Program { static void Main(string[] args) { var ts = new Test(); ts.exec1(); ts.exec2(); } } } ``` 在前面的示例中,我們在`exec1()`和`exec2()`方法之外定義了`x`變量。 該變量具有類作用域。 它在`Test`類的定義內的任何地方都有效,例如大括號之間。 ```cs public void exec1() { Console.WriteLine(this.x); Console.WriteLine(x); } ``` `x`變量(也稱為`x`字段)是一個實例變量。 因此,可以通過`this`關鍵字進行訪問。 它在`exec1()`方法中也有效,并且可以用其裸名引用。 這兩個語句都引用相同的變量。 ```cs public void exec2() { int z = 5; Console.WriteLine(x); Console.WriteLine(z); } ``` 也可以在`exec2()`方法中訪問 x 變量。 `z`變量在`exec2()`方法中定義。 它具有方法作用域。 僅在此方法中有效。 ```cs $ dotnet run 1 1 1 5 ``` 這是程序的輸出。 在方法內部定義的變量具有本地/方法作用域。 如果局部變量與實例變量具有相同的名稱,則它會遮蓋實例變量。 通過使用`this`關鍵字,類變量仍可在方法內部訪問。 `Program.cs` ```cs using System; namespace Shadowing { class Test { int x = 1; public void exec() { int x = 3; Console.WriteLine(this.x); Console.WriteLine(x); } } class Program { static void Main(string[] args) { var ts = new Test(); ts.exec(); } } } ``` 在前面的示例中,我們在`exec()`方法外部和`exec()`方法內部聲明`x`變量。 這兩個變量具有相同的名稱,但是它們沒有沖突,因為它們存在于不同的作用域內。 ```cs Console.WriteLine(this.x); Console.WriteLine(x); ``` 變量的訪問方式不同。 方法內定義的`x`變量(也稱為局部變量)僅通過其名稱即可訪問。 可以使用`this`關鍵字引用實例變量。 ```cs $ dotnet run 1 3 ``` This is the output of the program. ## C# 靜態方法 在沒有對象實例的情況下調用靜態方法。 要調用靜態方法,我們使用類的名稱和點運算符。 靜態方法只能與靜態成員變量一起使用。 靜態方法通常用于表示不會隨對象狀態變化的數據或計算。 數學庫是一個示例,其中包含用于各種計算的靜態方法。 我們使用`static`關鍵字聲明一個靜態方法。 如果不存在靜態修飾符,則該方法稱為實例方法。 我們不能在靜態方法中使用`this`關鍵字。 它只能在實例方法中使用。 `Main()`方法是 C# 控制臺和 GUI 應用的入口點。 在 C# 中,要求`Main()`方法是靜態的。 在應用啟動之前,尚未創建任何對象。 要調用非靜態方法,我們需要有一個對象實例。 靜態方法在實例化類之前就已存在,因此將靜態方法應用于主入口點。 `Program.cs` ```cs using System; namespace StaticMethod { class Basic { static int Id = 2321; public static void ShowInfo() { Console.WriteLine("This is Basic class"); Console.WriteLine("The Id is: {0}", Id); } } class Program { static void Main(string[] args) { Basic.ShowInfo(); } } } ``` 在我們的代碼示例中,我們定義了靜態`ShowInfo()`方法。 ```cs static int Id = 2321; ``` 靜態方法只能使用靜態變量。 ```cs public static void ShowInfo() { Console.WriteLine("This is Basic class"); Console.WriteLine("The Id is: {0}", Id); } ``` 這是我們的靜態`ShowInfo()`方法。 它與靜態 ID 成員一起使用。 ```cs Basic.ShowInfo(); ``` 要調用靜態方法,我們不需要對象實例。 我們通過使用類的名稱和點運算符來調用該方法。 ```cs $ dotnet run This is Basic class The Id is: 2321 ``` This is the output of the example. ## C# 隱藏方法 當派生類從基類繼承時,它可以定義基類中已經存在的方法。 我們說隱藏了我們從中派生的類的方法。 為了明確告知編譯器我們打算隱藏方法的意圖,我們使用`new`關鍵字。 沒有此關鍵字,編譯器將發出警告。 `Program.cs` ```cs using System; namespace HidingMethods { class Base { public void Info() { Console.WriteLine("This is Base class"); } } class Derived : Base { public new void Info() { base.Info(); Console.WriteLine("This is Derived class"); } } class Program { static void Main(string[] args) { var d = new Derived(); d.Info(); } } } ``` 我們有兩個類:`Derived`和`Base`類。 `Derived`類繼承自`Base`類。 兩者都有一種稱為`Info()`的方法。 ```cs class Derived : Base { ... } ``` (:)字符用于從類繼承。 ```cs public new void Info() { base.Info(); Console.WriteLine("This is Derived class"); } ``` 這是`Derived`類中`Info()`方法的實現。 我們使用`new`關鍵字通知編譯器我們正在從基類中隱藏方法。 請注意,我們仍然可以達到原始的`Info()`方法。 借助`base`關鍵字,我們也調用了`Base`類的`Info()`方法。 ```cs $ dotnet run This is Base class This is Derived class ``` 我們已經調用了這兩種方法。 ## C# 覆蓋方法 現在,我們將引入兩個新的關鍵字:`virtual`關鍵字和`override`關鍵字。 它們都是方法修飾符。 它們用于實現對象的多態行為。 `virtual`關鍵字創建一個虛擬方法。 可以在派生類中重新定義虛擬方法。 稍后在派生類中,我們使用`override`關鍵字重新定義相關方法。 如果派生類中的方法前面帶有`override`關鍵字,則派生類的對象將調用該方法,而不是基類方法。 `Program.cs` ```cs using System; namespace Overriding { class Base { public virtual void Info() { Console.WriteLine("This is Base class"); } } class Derived : Base { public override void Info() { Console.WriteLine("This is Derived class"); } } class Program { static void Main(string[] args) { Base[] objs = { new Base(), new Derived(), new Base(), new Base(), new Base(), new Derived() }; foreach (Base obj in objs) { obj.Info(); } } } } ``` 我們創建`Base`和`Derived`對象的數組。 我們遍歷數組并在所有數組上調用`Info()`方法。 ```cs public virtual void Info() { Console.WriteLine("This is Base class"); } ``` 這是`Base`類的虛擬方法。 期望在派生類中重寫它。 ```cs public override void Info() { Console.WriteLine("This is Derived class"); } ``` 我們將覆蓋`Derived`類中的基本`Info()`方法。 我們使用`override`關鍵字。 ```cs Base[] objs = { new Base(), new Derived(), new Base(), new Base(), new Base(), new Derived() }; ``` 在這里,我們創建`Base`和`Derived`對象的數組。 請注意,我們在數組聲明中使用了`Base`類型。 這是因為`Derived`類可以繼承,因此可以轉換為`Base`類。 相反的說法是不正確的。 將兩個對象放在一個數組中的唯一方法是對所有可能的對象使用在繼承層次結構中最頂層的類型。 ```cs foreach (Base obj in objs) { obj.Info(); } ``` 我們遍歷數組,并在數組中的所有對象上調用`Info()`。 ```cs $ dotnet run This is Base class This is Derived class This is Base class This is Base class This is Base class This is Derived class ``` 這是輸出。 現在,將`new`關鍵字更改為`override`關鍵字。 再次編譯該示例并運行它。 ```cs $ dotnet run This is Base class This is Base class This is Base class This is Base class This is Base class This is Base class ``` 這次我們有不同的輸出。 ## C# 本地函數 C# 7.0 引入了本地功能。 這些是在其他方法中定義的函數。 `Program.cs` ```cs using System; namespace LocalFunction { class Program { static void Main(string[] args) { Console.Write("Enter your name: "); string name = Console.ReadLine(); string message = BuildMessage(name); Console.WriteLine(message); string BuildMessage(string value) { string msg = String.Format("Hello {0}!", value); return msg; } } } } ``` 在示例中,我們有一個局部函數`BuildMessage()`,它在`Main()`方法內部定義和調用。 ## C# 密封方法 密封方法將覆蓋具有相同簽名的繼承虛擬方法。 密封方法也應標有倍率修飾符。 使用`sealed`修飾符可防止派生類進一步覆蓋該方法。 和這兩個字很重要。 首先,方法必須是虛擬的。 必須稍后將其覆蓋。 至此,可以將其密封。 `Program.cs` ```cs using System; namespace SealedMethods { class A { public virtual void F() { Console.WriteLine("A.F"); } public virtual void G() { Console.WriteLine("A.G"); } } class B : A { public override void F() { Console.WriteLine("B.F"); } public sealed override void G() { Console.WriteLine("B.G"); } } class C : B { public override void F() { Console.WriteLine("C.F"); } /*public override void G() { Console.WriteLine("C.G"); }*/ } class SealedMethods { static void Main(string[] args) { B b = new B(); b.F(); b.G(); C c = new C(); c.F(); c.G(); } } } ``` 在前面的示例中,我們密封了類`B`中的方法`G()`。 ```cs public sealed override void G() { Console.WriteLine("B.G"); } ``` 方法`G()`會覆蓋`B`類的祖先中具有相同名稱的方法。 它也被密封以防止進一步取代該方法。 ```cs /*public override void G() { Console.WriteLine("C.G"); }*/ ``` 這些行被注釋,因為否則代碼示例將無法編譯。 編譯器將給出以下錯誤:`Program.cs`(38,30):錯誤 CS0239:`C.G()`:無法覆蓋繼承的成員`B.G()`,因為它是密封的 ```cs c.G(); ``` 此行將`"B.G()"`打印到控制臺。 ```cs $ dotnet run B.F B.G C.F B.G ``` This is the output. ## C# 方法的表達式主體定義 方法的表達主體定義使我們能夠以非常簡潔,易讀的形式定義方法實現。 ```cs method declaration => expression ``` 這是一般語法。 `Program.cs` ```cs using System; namespace ExpBodyDef { class User { public string Name { get; set; } public string Occupation { get; set; } public override string ToString() => $"{Name} is a {Occupation}"; } class Program { static void Main (string[] args) { var user = new User(); user.Name = "John Doe"; user.Occupation = "gardener"; Console.WriteLine(user); } } } ``` 在示例中,我們為`ToString()`方法的主體提供了一個表達式主體定義。 ```cs public override string ToString() => $"{Name} is a {Occupation}"; ``` 表達式主體定義簡化了語法。 在 C# 教程的這一部分中,我們介紹了方法。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看