C#教程8:面向对象编程【02】
十、C#?表達式體構(gòu)造函數(shù)
可以創(chuàng)建表達式主體的構(gòu)造函數(shù);它們提供了更簡潔、更好看的語法。
Program.cs
var u1 = new User("John Doe", "gardener"); var u2 = new User("Roger Roe", "driver");Console.WriteLine(u1); Console.WriteLine(u2);class User {private string Name;private string Occupation;public User(string Name, string Occupation) =>(this.Name, this.Occupation) = (Name, Occupation);public override string ToString() =>$"User {{ {this.Name} {this.Occupation} }}"; }我們有一個帶有兩個參數(shù)的構(gòu)造函數(shù);它們被設置在一個表達式主體中。
public User(string Name, string Occupation) =>(this.Name, this.Occupation) = (Name, Occupation);在這種情況下,this 關(guān)鍵字是必需的。
十一、C#?目標類型的new表達式
當類型已知時,目標類型的新表達式不需要為構(gòu)造函數(shù)指定類型。此功能是在 C# 9.0 中引入的。
Program.cs
var u1 = new User("Roger", "Roe", "driver"); Console.WriteLine(u1);User u2 = new("John", "Doe", "gardener"); Console.WriteLine(u2);var users = new List<User> {new("Thomas", "Roove", "programmer"),new("Lucia", "Smith", "hair dresser"),new("Peter", "Holcomb", "painter"),new("Orlando", "Black", "actor"),new("Patrick", "Allen", "police officer") };foreach (var user in users) {Console.WriteLine(user); }class User {public string FirstName { get; set; }public string LastName { get; set; }public string Occupation { get; set; }public User(string FirstName, string LastName, string Occupation) =>(this.FirstName, this.LastName, this.Occupation) = (FirstName, LastName, Occupation);public override string ToString() =>$"User {{ {this.FirstName} {this.LastName} {this.Occupation} }}"; }我們演示了用戶類型的目標類型新表達式。
var u1 = new User("Roger", "Roe", "driver");var 關(guān)鍵字可用于省略賦值左側(cè)的類型聲明,因為編譯器可以從右側(cè)推斷類型。
User u2 = new("John", "Doe", "gardener");目標類型的新表達式允許我們省略賦值右側(cè)的類型聲明。
var users = new List<User> {new("Thomas", "Roove", "programmer"),new("Lucia", "Smith", "hair dresser"),new("Peter", "Holcomb", "painter"),new("Orlando", "Black", "actor"),new("Patrick", "Allen", "police officer") };在列表初始化器中,我們通過省略每個用戶的類型來節(jié)省一些擊鍵。
十二、C#類常量
C# 允許創(chuàng)建類常量。這些常量不屬于具體對象。他們屬于階級。按照慣例,常量用大寫字母書寫。
Program.cs
Console.WriteLine(Math.PI);class Math {public const double PI = 3.14159265359; }我們有一個帶有 PI 常數(shù)的數(shù)學課。
public const double PI = 3.14159265359;const 關(guān)鍵字用于定義常量。 public 關(guān)鍵字使其可以在類主體之外訪問。
$ dotnet run 3.14159265359十三、C#繼承
????????繼承是一種使用已經(jīng)定義的類來形成新類的方法。新形成的類稱為派生類,我們派生的類稱為基類。繼承的重要好處是代碼重用和降低程序的復雜性。派生類(后代)覆蓋或擴展基類(祖先)的功能。
Program.cs
new Human();class Being {public Being(){Console.WriteLine("Being is created");} }class Human : Being {public Human(){Console.WriteLine("Human is created");} }在這個程序中,我們有兩個類。基礎存在類和派生人類類。派生類繼承自基類。
new Human();我們實例化派生的 Human 類。
class Human : Being在 C# 中,我們使用冒號 (:) 運算符來創(chuàng)建繼承關(guān)系。
$ dotnet run Being is created Human is created????????我們可以看到兩個構(gòu)造函數(shù)都被調(diào)用了。首先調(diào)用基類的構(gòu)造函數(shù),然后調(diào)用派生類的構(gòu)造函數(shù)。
????????下面是一個更復雜的例子。
Program.cs
new Human();var dog = new Dog(); dog.GetCount();class Being {static int count = 0;public Being(){count++;Console.WriteLine("Being is created");}public void GetCount(){Console.WriteLine("There are {0} Beings", count);} }class Human : Being {public Human(){Console.WriteLine("Human is created");} }class Animal : Being {public Animal(){Console.WriteLine("Animal is created");} }class Dog : Animal {public Dog(){Console.WriteLine("Dog is created");} }????????我們有四個類。繼承層次更復雜。人類和動物類繼承自存在類。 Dog 類直接繼承自 Animal 類,間接繼承自 Being 類。我們還引入了靜態(tài)變量的概念。
new Human();var dog = new Dog(); dog.GetCount();我們從人類和狗類創(chuàng)建實例。我們調(diào)用 Dog 對象的 GetCount 方法。
static int count = 0;我們定義了一個靜態(tài)變量。靜態(tài)成員是類的所有實例共享的成員。
Being() {count++;Console.WriteLine("Being is created"); }每次實例化存在類時,我們將計數(shù)變量加一。這樣我們就可以跟蹤創(chuàng)建的實例數(shù)量。
class Animal : Being ...class Dog : Animal ...動物繼承了存在,狗繼承了動物。間接地,狗也繼承了存在。
$ dotnet run Being is created Human is created Being is created Animal is created Dog is created There are 2 Beings人類調(diào)用了兩個構(gòu)造函數(shù)。 Dog 調(diào)用了三個構(gòu)造函數(shù)。實例化了兩個存有。
我們使用 base 關(guān)鍵字顯式調(diào)用父級的構(gòu)造函數(shù)。
Program.cs
var c = new Circle(2, 5, 6); Console.WriteLine(c);class Shape {protected int x;protected int y;public Shape(){Console.WriteLine("Shape is created");}public Shape(int x, int y){this.x = x;this.y = y;} }class Circle : Shape {private int r;public Circle(int r, int x, int y) : base(x, y){this.r = r;}public override string ToString(){return String.Format("Circle, r:{0}, x:{1}, y:{2}", r, x, y);} }????????我們有兩個類:Shape 類和 Circle 類。 Shape 類是幾何形狀的基類。我們可以在這個類中加入一些常見形狀的共性,比如 x 和 y 坐標。
public Shape() {Console.WriteLine("Shape is created"); }public Shape(int x, int y) {this.x = x;this.y = y; }Shape 類有兩個構(gòu)造函數(shù)。第一個是默認構(gòu)造函數(shù)。第二個有兩個參數(shù):x,y 坐標。
public Circle(int r, int x, int y) : base(x, y) {this.r = r; }????????這是 Circle 類的構(gòu)造函數(shù)。此構(gòu)造函數(shù)初始化 r 成員并調(diào)用父級的第二個構(gòu)造函數(shù),并將 x、y 坐標傳遞給該構(gòu)造函數(shù)。如果我們沒有使用 base 關(guān)鍵字顯式調(diào)用構(gòu)造函數(shù),則會調(diào)用 Shape 類的默認構(gòu)造函數(shù)。
$ dotnet run Circle, r:2, x:5, y:6十四、C#抽象類和方法
抽象類不能被實例化。如果一個類至少包含一個抽象方法,它也必須聲明為抽象的。抽象方法無法實現(xiàn);他們只是聲明方法的簽名。當我們從抽象類繼承時,所有抽象方法都必須由派生類實現(xiàn)。此外,這些方法必須聲明為具有較少限制的可見性。
與接口不同,抽象類可能具有完全實現(xiàn)的方法,也可能具有定義的成員字段。所以抽象類可以提供部分實現(xiàn)。程序員經(jīng)常將一些通用功能放入抽象類中。這些抽象類后來被子類化以提供更具體的實現(xiàn)。
例如,Qt 圖形庫有一個 QAbstractButton,它是按鈕小部件的抽象基類,提供按鈕共有的功能。按鈕 Q3Button、QCheckBox、QPushButton、QRadioButton 和 QToolButton 繼承自此基本抽象類。
正式地說,抽象類用于執(zhí)行協(xié)議。協(xié)議是所有實現(xiàn)對象必須支持的一組操作。
Program.cs
namespace AbstractClass;abstract class Drawing {protected int x = 0;protected int y = 0;public abstract double Area();public string GetCoordinates(){return string.Format("x: {0}, y: {1}", this.x, this.y);} }class Circle : Drawing {private int r;public Circle(int x, int y, int r){this.x = x;this.y = y;this.r = r;}public override double Area(){return this.r * this.r * Math.PI;}public override string ToString(){return string.Format("Circle at x: {0}, y: {1}, radius: {2}",this.x, this.y, this.r);} }class Program {static void Main(string[] args){var c = new Circle(12, 45, 22);Console.WriteLine(c);Console.WriteLine("Area of circle: {0}", c.Area());Console.WriteLine(c.GetCoordinates());} }????????我們有一個抽象的基礎繪圖類。該類定義了兩個成員字段,定義了一種方法并聲明了一種方法。其中一種方法是抽象的,另一種是完全實現(xiàn)的。繪圖類是抽象的,因為我們無法繪制它。我們可以畫一個圓、一個點或一個正方形。繪圖類對我們可以繪制的對象有一些共同的功能。
namespace AbstractClass;命名空間用于組織代碼。文件中定義的類屬于 AbstractClass 命名空間。
abstract class Drawing我們使用 abstract 關(guān)鍵字來定義一個抽象類。
public abstract double Area();抽象方法前面也有抽象關(guān)鍵字。
class Circle : Drawing圓是繪圖類的子類。它必須實現(xiàn)抽象區(qū)域方法。
public override double Area() {return this.r * this.r * Math.PI; }????????當我們實現(xiàn)區(qū)域方法時,我們必須使用覆蓋關(guān)鍵字。這樣我們通知編譯器我們覆蓋了一個現(xiàn)有的(繼承的)方法。
$ dotnet run Circle at x: 12, y: 45, radius: 22 Area of circle: 1520.53084433746 x: 12, y: 45十五、C#部分類
????????使用部分關(guān)鍵字,可以將類的定義拆分為同一命名空間內(nèi)的多個部分。該類也可以在多個文件中定義。
????????在處理非常大的代碼庫時使用部分類,可以將其拆分為更小的單元。部分類也與自動代碼生成器一起使用。
Program.cs
namespace PartialClass;partial class Worker {public string DoWork(){return "Doing work";} }partial class Worker {public string DoPause(){return "Pausing";} }class Program {static void Main(string[] args){var worker = new Worker();Console.WriteLine(worker.DoWork());Console.WriteLine(worker.DoWork());Console.WriteLine(worker.DoPause());} }在示例中,我們將 Worker 類定義為兩部分。編譯器將這些部分連接在一起以形成最終類。
$ dotnet run Doing work Doing work Pausing總結(jié)
以上是生活随笔為你收集整理的C#教程8:面向对象编程【02】的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: C#教程8:面向对象编程【01】
- 下一篇: 基础数学:关于二次无理数