日期:2008-6-9
學習內容:構造器,類的修飾符,虛方法,抽象類
遺留問題:
學習總結:
1. 構造器
知識點一:構造器從來都沒有返回值,其中不能包含return語句(一般的成員方法要在方法名稱前面加上void關鍵字,而構造器不用)
知識點二:類中的成員變量如果不對其進行初始化(即賦值),如果爲int型的成員變量,則默認初始化爲0,string在默認初始化爲NULL
知識點三:類中的成員變量不賦值即可使用,而局部變量必須賦初值後纔可使用
知識點四:this關鍵字,this是C#中隱含的指針,當類實例化時把對象的地址賦值給this
知識點五:實際開發中帶參數的構造器中的參數名稱最好和成員變量名稱不同,如果相同必須加上this關鍵字加以區別,this.i代表成員變量,i代表是構造器中的參數
知識點六:如果在聲明成員變量時給成員變量賦了初值,且構造器的重載個數較多,會產生大量的代碼冗餘(可以通過MIL查看,有大量重複代碼)消除冗餘的方法:將成員變量在無參構造器中進行初始化,然後用有參構造器調用無參構造器,調用無參構造器的方法:在有參構造器的後面加上:this(),再通過MIL查看中間代碼,冗餘消失了。
實例代碼:
using System;
namespace ConsoleApplication1
{
class A
{
public int i;//聲明兩個成員變量
public string s;
public A()//無參構造器,並對成員變量進行初始化
{
i = 100;
s = "我的夢想是一名程序員";
}
public A(int _i):this()//有參數的構造器,並調用無參構造器
{
i = _i;
}
public A(string _s):this()
{
s=_s;
}
}
class Test
{
static void Main (string[] args)
{
A a = new A(200);
Console.WriteLine(a.i);
A a1=new A("程序呀");
Console.WriteLine(a1.s);
}
}
}
知識點七:在類的繼承中,派生類在實例化時,先執行父類的無參構造器,才執行自己的構造器
知識點八:只有基類的無參構造器會被繼承,有參構造器不被繼承
知識點九:建立類時會自動生成一個無參數的構造器,但如果定義了有參數的構造器,就不生成無參數的構造器了
知識點十:引用父類的構造器的方法::base(參數)
知識點十一:在一個程序執行的過程中,靜態構造器最多執行一次;靜態構造器在類的靜態成員初始化後執行(或者講編譯器會將靜態成員初始化語句轉換成賦值語句放在靜態構造器執行的最開始);靜態構造器在任何類的靜態成員被引用之前執行;靜態構造器在任何類的實例變量被分配之前執行。
2. 類的修飾符
訪問修飾符 |
類內部 |
子類 |
程序集內 |
程序集外 |
default |
可以 |
|
|
|
public |
可以 |
可以 |
可以 |
可以 |
private |
可以 |
|
|
|
internal |
可以 |
可以 |
可以 |
|
protected |
可以 |
可以 |
|
|
Protected internal |
可以 |
可以 |
可以 |
|
注意:關鍵字class前面如果沒有修飾符默認爲internal,類的成員前面如果沒有修飾符默認爲private
Sealed訪問修飾符說明此類不能被繼承
3. 虛方法
使用虛方法的實例:
using System;
namespace ConsoleApplication1
{
class Employee
{
protected string _name;
public Employee()
{
}
public Employee(string name)
{
_name = name;
}
public virtual void StartWork() //虛方法
{
Console.Write(_name+"開始工作:");
}
}
class Manager : Employee
{
public Manager(string name) : base(name) { }//繼承父類的帶參數的構造方法
public override void StartWork() //虛方法重寫
{
base.StartWork();
Console.WriteLine("給員工下達任務");
}
}
class Seller : Employee
{
public Seller(string name) : base(name) { }
public override void StartWork()
{
base.StartWork();
Console.WriteLine("銷售產品");
}
}
class Test
{
static void Main (string[] args)
{
Employee[] emp = new Employee[4];//employee類的對象數組,存儲的是地址值
emp[0] = new Manager("張三");
emp[1] = new Seller("李四");
emp[2] = new Manager("王五");
emp[3] = new Seller("趙六");
Console.WriteLine("早上8點開始工作:");
foreach (Employee e in emp)
{
e.StartWork();
}
}
}
}
4. 抽象類
知識點一:抽象類不能被實例化
知識點二:抽象類可以包含抽象方法和抽象訪問器
知識點三:抽象方法本質上就是一個虛方法,用以實現多態
知識點四:不能用sealed修飾符修改抽象類,派生類必須全部實現抽象類定義的抽象方法和抽象訪問器
抽象方法:
1. 抽象方法是隱式的虛方法
2. 只允許在抽象類中使用抽象方法聲明
3. 因爲抽象方法聲明不提供實際的實現,所以沒有方法體:方法聲明只是以一個分好結束,並且在簽名後沒有大括號({}),實現由一個重寫方法提供,此重寫方法是非抽象類的成員
4. 在抽象方法聲明中使用static或virtual修飾符是錯誤的
5. 除了在聲明和調用語法上不同外,抽象屬性的行爲與抽象方法一樣
6. 在靜態屬性上使用abstract修飾符是錯誤的
7. 在派生類中,通過包括使用override修飾符的屬性聲明,可以重寫抽象的繼承屬性
抽象類的構造函數:
任何情況下,抽象類都不應進行實例化,因此,正確定義其構造函數就非常重要。確保抽象類功能的正確性和擴展性也很重要。下列準則有助於確保抽象類能夠正確的設計並在實現後可以按預期的方式工作。
1. 不要在抽象類中定義公共的或受保護的構造函數,具有public或protected internal可見性的構造函數用於能進行實例化的類型。任何情況下抽象類型不能實例化。
2. 應在抽象類中定義一個受保護(protected)構造函數或內部(private)構造函數
3. 如果在抽象類中定義一個受保護構造函數,則在創建派生類的實例時,基類可以執行初始化任務
抽象方法和虛方法的區別:
1. 抽象方法和虛方法的區別在於:虛方法有一個實現部分,併爲派生類提供了覆蓋該方法的選項,相反,抽象方法沒有提供實現部分,強制派生類覆蓋方法(否則派生類不能稱爲具體類)
2. abstract方法只能在抽象類中聲明,虛方法則不是
3. abstract方法必須在派生類中重寫,而virtual則不必
4. abstract方法不能聲明方法體,虛方法則可以
抽象類的例子:
using System;
namespace ConsoleApplication1
{
abstract class Employee
{
protected string _name;
protected Employee()
{
}
protected Employee(string name)
{
_name = name;
}
public abstract void StartWork(); //虛方法
}
class Manager : Employee
{
public Manager(string name) : base(name) { }//繼承父類的帶參數的構造方法
public override void StartWork() //虛方法重寫
{
Console.WriteLine(_name+"開始工作:"+"給員工下達任務");
}
}
class Seller : Employee
{
public Seller(string name) : base(name) { }
public override void StartWork()
{
Console.WriteLine(_name+"開始工作:"+"銷售產品");
}
}
class Test
{
static void Main (string[] args)
{
Employee[] emp = new Employee[4];//employee類的對象數組,存儲的是地址值
emp[0] = new Manager("張三");
emp[1] = new Seller("李四");
emp[2] = new Manager("王五");
emp[3] = new Seller("趙六");
Console.WriteLine("早上8點開始工作:");
foreach (Employee e in emp)
{
e.StartWork();
}
}
}
}
從以上代碼可以看到存在大量重複的代碼,因此此實例不適合用抽象類實現,這裏知識爲了演示抽象類的用法