詳解C++ 多態(tài)的兩種形式(靜態(tài)、動態(tài))
1.多態(tài)的概念與分類
多態(tài)(Polymorphisn)是面向對象程序設計(OOP)的一個重要特征。多態(tài)字面意思為多種狀態(tài)。在面向對象語言中,一個接口,多種實現(xiàn)即為多態(tài)。C++中的多態(tài)性具體體現(xiàn)在編譯和運行兩個階段。編譯時多態(tài)是靜態(tài)多態(tài),在編譯時就可以確定使用的接口。運行時多態(tài)是動態(tài)多態(tài),具體引用的接口在運行時才能確定。
靜態(tài)多態(tài)和動態(tài)多態(tài)的區(qū)別其實只是在什么時候將函數(shù)實現(xiàn)和函數(shù)調(diào)用關聯(lián)起來,是在編譯時期還是運行時期,即函數(shù)地址是早綁定還是晚綁定的。靜態(tài)多態(tài)是指在編譯期間就可以確定函數(shù)的調(diào)用地址,并生產(chǎn)代碼,這就是靜態(tài)的,也就是說地址是早綁定。靜態(tài)多態(tài)往往也被叫做靜態(tài)聯(lián)編。 動態(tài)多態(tài)則是指函數(shù)調(diào)用的地址不能在編譯器期間確定,需要在運行時確定,屬于晚綁定,動態(tài)多態(tài)往往也被叫做動態(tài)聯(lián)編。
2.多態(tài)的作用
為何要使用多態(tài)呢?封裝可以使得代碼模塊化,繼承可以擴展已存在的代碼,他們的目的都是為了代碼重用。而多態(tài)的目的則是為了接口重用。靜態(tài)多態(tài),將同一個接口進行不同的實現(xiàn),根據(jù)傳入不同的參數(shù)(個數(shù)或類型不同)調(diào)用不同的實現(xiàn)。動態(tài)多態(tài),則不論傳遞過來的哪個類的對象,函數(shù)都能夠通過同一個接口調(diào)用到各自對象實現(xiàn)的方法。
3.靜態(tài)多態(tài)
靜態(tài)多態(tài)往往通過函數(shù)重載和模版(泛型編程)來實現(xiàn),具體可見下面代碼:
#include <iostream> using namespace std; //兩個函數(shù)構成重載 int add(int a, int b) { cout<<"in add_int_int()"<<endl; return a + b; } double add(double a, double b) { cout<<"in add_double_doube()"<<endl; return a + b; } //函數(shù)模板(泛型編程) template <typename T> T add(T a, T b) { cout<<"in func tempalte"<<endl; return a + b; } int main() { cout<<add(1,1)<<endl; //調(diào)用int add(int a, int b) cout<<add(1.1,1.1)<<endl; //調(diào)用double add(double a, double b) cout<<add<char>('A',' ')<<endl; //調(diào)用模板函數(shù),輸出小寫字母a }
程序輸出結果:
in add_int_int()
2
in add_double_doube()
2.2
in func tempalte
a
4.動態(tài)多態(tài)
動態(tài)多態(tài)最常見的用法就是聲明基類的指針,利用該指針指向任意一個子類對象,調(diào)用相應的虛函數(shù),可以根據(jù)指向的子類的不同而調(diào)用不同的方法。如果沒有使用虛函數(shù),即沒有利用C++多態(tài)性,則利用基類指針調(diào)用相應函數(shù)的時候,將總被限制在基類函數(shù)本身,而無法調(diào)用到子類中被重寫過的函數(shù)。因為沒有多態(tài)性,函數(shù)調(diào)用的地址將是一定的,而固定的地址將始終調(diào)用同一個函數(shù),這就無法“實現(xiàn)一個接口,多種實現(xiàn)”的目的了。
#include <iostream> using namespace std; class Base { public: virtual void func() { cout << "Base::fun()" << endl; } }; class Derived : public Base { public: virtual void func() { cout << "Derived::fun()" << endl; } }; int main() { Base* b=new Derived; //使用基類指針指向派生類對象 b->func(); //動態(tài)綁定派生類成員函數(shù)func Base& rb=*(new Derived); //也可以使用引用指向派生類對象 rb.func(); }
程序輸出結果:
Derived::fun()
Derived::fun()
通過上面的例子可以看出,在使用基類指針或引用指向子類對象時,調(diào)用的函數(shù)是子類中重寫的函數(shù),這樣就實現(xiàn)了運行時函數(shù)地址的動態(tài)綁定,即動態(tài)聯(lián)編。動態(tài)多態(tài)是通過“繼承+虛函數(shù)”來實現(xiàn)的,只有在程序運行期間(非編譯期)才能判斷所引用對象的實際類型,根據(jù)其實際類型調(diào)用相應的方法。具體格式就是使用virtual關鍵字修飾類的成員函數(shù)時,指明該函數(shù)為虛函數(shù),并且派生類需要重新實現(xiàn)該成員函數(shù),編譯器將實現(xiàn)動態(tài)綁定。
以上就是詳解C++ 多態(tài)的兩種形式(靜態(tài)、動態(tài))的詳細內(nèi)容,更多關于C++ 靜態(tài)多態(tài)和動態(tài)多態(tài)的資料請關注腳本之家其它相關文章!
相關文章
在Ubuntu中安裝VSCode并配置C/C++開發(fā)環(huán)境的方法步驟
這篇文章主要介紹了在Ubuntu中安裝VSCode并配置C/C++開發(fā)環(huán)境的方法步驟,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧2020-05-05C/C++實現(xiàn)枚舉網(wǎng)上鄰居信息的示例詳解
在Windows系統(tǒng)中,通過網(wǎng)絡鄰居可以方便地查看本地網(wǎng)絡中的共享資源和計算機,本文將介紹一個簡單的C++程序,使用Windows API枚舉網(wǎng)絡鄰居信息,并獲取對端名稱、本機名稱、主機名稱以及主機IP等信息,文中通過代碼示例給大家講解非詳細,需要的朋友可以參考下2023-12-12