c struct 建構函式

2021-06-04 04:51:02 字數 1570 閱讀 9518

struct test

;int main()

7: test()

10: 

void fun()

13:  };

14:  int main()

15: 

找出這個程式錯誤的一行?

答案很簡單就是第19行,往下看就知道為什麼啦!

結構是一種用關鍵字struct宣告的自定義資料型別。與類相似,也可以包含建構函式,常數,字段,方法,屬性,索引器,運算子和巢狀型別等,不過,結構是值型別。但是,c++的結構和類是有區別的:

1、結構的建構函式和類的建構函式不同。

a.結構不能包含顯式的無引數建構函式。結構成員講自動初始化為它們的預設值。

b.結構不能包含以下形式的初始值設定類:base(argument-list);

2、對於結構中的例項字段成員,不能在宣告時賦值初始化。

3、宣告了結構型別後,可以使用new運算子建立構造物件,也可以不使用new,如果不使用new,那麼在初始化所有字段之前,欄位將保持未賦值狀態且物件不可用。

4、結構不支援繼承,即乙個結構不能從另乙個結構或類繼承,而且不能作為乙個類的基類。但是,結構從基類object繼承。結構也可以實現介面。

從編譯角度來思考下:

摘自csdn:

最近才知道struct和class的靜態建構函式的觸發規則是不同的,不像class在第一次使用類的時候觸發靜態建構函式。如果只訪問struct例項的字段是不會觸發靜態構造函式呼叫的。通過測試發現當訪問靜態字段,struct本身的函式(靜態和例項)和帶引數的建構函式就會引起靜態建構函式的執行。而呼叫預設構造和未覆寫的基類虛函式是不會的。為什麼呢?

讓我們先來看看class和struct在呼叫建構函式時的區別。class使用newobj指令而struct使用initobj指令來構造物件。newobj在堆上申請一塊記憶體並呼叫相應的建構函式進行初始化,然後將物件位址返回給計算棧。initobj則是從本地變數表中載入已經分配出來的struct例項然後初始化struct的各欄位。這個初始化過程是clr內部執行的,而不像class編譯器會給class新增乙個預設建構函式(這就是為什麼struct不能給字段新增預設值的原因。但在類中如果給字段新增了預設值編譯器就會自動在建構函式中新增字段賦值操作)。如果給struct中定義了乙個有引數的建構函式,那麼系統就不會使用initobj指令,而是直接用call指令呼叫帶引數的建構函式。

我們最常見最常用的呼叫函式的指令是call和callvirt。對於靜態函式使用call指令,對於class使用callvirt指令(不論class中的函式是不是虛的)。只有子類呼叫父類的函式的時候(避免遞迴呼叫)以及建構函式中(由編譯器新增保證父類字段被初始化)使用call指令。而對於struct我們發現只要呼叫的函式是struct本身定義的都是使用call指令。call和callvirt指令的差別在於,call會把呼叫的函式當作靜態函式看待,而不會關心呼叫當前函式時例項指標(this)是否為空。這就是struct呼叫函式時為什麼都是call因為struct例項是不可能被置為null的。實際上class在呼叫非虛函式時實際上也是使用call的只是多做了一步驗證——this是否為空,讓我們來驗證一下。

C struct裡定義函式

在做乙個小的程式題的時候,看到了struct中定義了函式,之前沒有看到過,所以查了一點相關的知識,在這裡記錄一下 c 中允許在結構體當中定義函式,它的用法和類的用法很像,不過與類有乙個區別在於,struct中定義的函式和變數都是預設為public的,但class中的則是預設為private。incl...

C struct結構型別

struct 結構 型別,是一種複雜的資料型別。它可以包含簡單資料型別,也可以包含其他結構型別,以及方法 屬性 索引器等。1 struct結構型別是值型別,這也是與類最重要的區別。2 結構型別可以實現介面,卻無法繼承另外乙個結構。3 結構型別成員,不能被宣告為protected。4 結構型別中,不能...

建構函式 拷貝建構函式 賦值建構函式

class和struct很大乙個區別在於,c除了成員的訪問控制許可權,struct中的成員預設是public,而class中的field預設是private class還有乙個special的地方是它有建構函式 constructor。建構函式是class中的一員,和成員變數 其他成員函式一起構成乙...