1.什么是虛函數(shù)?
用virtual
修飾的成員函數(shù)叫虛函數(shù)
小知識: 沒有虛構造函數(shù) 不寫虛函數(shù),沒有默認的虛函數(shù)
普通函數(shù)不影響類的內存:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
|
class MM { public : void print() { cout << "普通函數(shù)" << endl; //普通函數(shù)不影響類的內存<--->普通函數(shù)存在另一段內存中 } protected : }; void testVirtual() { //C語言不允許存在空的結構體 cout << sizeof (MM) << endl; /*(沒有數(shù)據成員的)空的類或者結構體 占用1字節(jié) 用1字節(jié)標識當 前內存為結構體內存*/ } int main() { testVirtual(); return 0; } /*輸出*/ /* 1 */ |
2.虛函數(shù)會影響類的內存
增加一個指針的內存,32位操作系統(tǒng)多4個字節(jié) ,64位操作系統(tǒng)多8個字節(jié)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
#include <iostream> using namespace std; class MM { public : virtual void print1() { cout << "虛函數(shù)1" << endl; } /*virtual void print2() { cout << "虛函數(shù)2" << endl; } 無論多少個虛函數(shù),增加的字節(jié)就是一個指針的字節(jié)--->多了一個虛函數(shù),還是4個字節(jié)*/ protected : }; void testVirtual() { cout << sizeof (MM) << endl; } int main() { testVirtual(); return 0; } /*輸出*/ /* 4 */ |
小知識:一旦有了數(shù)據,標識位就不需要存在了
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
|
class A { int num; //輸出4而不是5 (4+1) }; class B { //用1字節(jié)標識當前內存為結構體內存 }; void testVirtual() { cout << sizeof (A) << endl; cout << sizeof (B) << endl; } int main() { testVirtual(); return 0; } /*輸出*/ /*4 1*/ |
3.了解虛函數(shù)表--->通過虛函數(shù)表的指針去訪問數(shù)據
就是一個指針存儲所有虛函數(shù)的首地址(虛函數(shù)函數(shù)名)<--->函數(shù)指針
只有指針可以操作一段內存(4字節(jié))
/*無論多少個虛函數(shù),增加的字節(jié)就是一個指針的字節(jié)*/
所有的虛函數(shù)其實是 用一個函數(shù)指針去存儲的 ,把 這個函數(shù)指針指向的這一段內存 稱為虛函數(shù)表
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
|
#include <iostream> using namespace std; class MM { public : virtual void print1() { cout << "虛函數(shù)1" << endl; } virtual void print2() { cout << "虛函數(shù)2" << endl; } protected : }; void testVirtual() { //虛函數(shù)表 MM mm; //構建一個對象 int ** vptr = ( int ** )&mm; //定義一個二級指針&對象的地址 強轉類型 typedef void (*PF)(); //函數(shù)指針定義別名 PF func = (PF)vptr[0][0]; //把地址轉為函數(shù)指針,訪問第一個函數(shù)指針的地址 func(); //通過虛函數(shù)表的函數(shù)指針調用第一個虛函數(shù) func = (PF)vptr[0][1]; func(); //調用第二個虛函數(shù) } int main() { testVirtual(); return 0; } /*輸出*/ /*虛函數(shù)1 虛函數(shù)2*/ |
4.虛函數(shù)聲明
虛函數(shù)可以在類中聲明,在類外實現(xiàn),不再需要virtual
修飾詞,只要類名限定就可以了
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
class MM { public : virtual void print3(); protected : }; void MM::print3() { cout << "虛函數(shù)3" << endl; } int main() { MM mm; mm.print3(); return 0; } /*輸出*/ /*虛函數(shù)3*/ |
到此這篇關于c++虛函數(shù)與虛函數(shù)表原理的文章就介紹到這了,更多相關c++虛函數(shù)與虛函數(shù)表內容請搜索服務器之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持服務器之家!
原文鏈接:https://blog.csdn.net/weixin_60569662/article/details/121722479