結構體的巢狀問題
結構體的自引用(self reference),就是在結構體內部,包含指向自身型別結構體的指標。
結構體的相互引用(mutual reference),就是說在多個結構體中,都包含指向其他結構體的指標。
1.1不使用typedef時
錯誤的方式:
struct這種宣告是錯誤的,因為這種宣告實際上是乙個無限迴圈,成員a是乙個結構體,a的內部還會有成員是結構體,依次下去,無線迴圈。在分配記憶體的時候,由於無限巢狀,也無法確定這個結構體的長度,所以這種方式是非法的。tag_1;
正確的方式:(使用指標)
struct由於指標的長度是確定的(在32位機器上指標長度為4),所以編譯器能夠確定該結構體的長度。tag_1;
1.2 使用typedef 時
錯誤的方式:
typedef struct這裡的目的是使用typedef為結構體建立乙個別名nodep。但是這裡是錯誤的,因為型別名的作用域是從語句的結尾開始,而在結構體內部是不能使用的,因為還沒定義。node;
正確的方式:有三種,差別不大,使用哪種都可以。
typedef struct2. 相互引用 結構體tag_1 node;
struct
tag_2;
typedef
struct
tag_2 node;
struct
tag_2;
struct
tag_3;
typedef
struct tag_3 node;
錯誤的方式:
typedef struct錯誤的原因和上面一樣,這裡型別b在定義之前 就被使用。tag_a a;
typedef
struct
tag_b b;
正確的方式:(使用「不完全宣告」)
struct巢狀結構體時應注意:tag_a;
struct
tag_b;
typedef
struct
tag_a a;
typedef
struct
tag_b b;
struct
tag_a;
struct
tag_b;
typedef
struct
tag_a a;
typedef
struct
tag_b b;
struct
tag_a;
struct
tag_b;
結構體的自引用中,如下這種情況是非法的
struct s_ref ;
因為結構體內部又包含自身結構體型別b,這個長度不能確定,只能向下再查詢,又包含自身結構體型別b,又再向下查詢,如此迴圈,類似於永無出口的遞迴呼叫,是非法的。
但很多時候,的確需要使用到自引用,有個技巧,如下:
struct s_ref ;
這是合法的,因為此處是定義了乙個指向結構體的指標,指標的大小在具體的機器平台和編譯器環境中都是已知的(即使不同的平台環境的定義不完全相同)。所以不會導致上述的遞迴死迴圈。是合法和可行的。但是要提醒的是:這個指標看似指向自身,其實不是,而是指向同一型別的不同結構。
鍊錶和樹的資料結構就都使用到此技巧。自身的結構體指標指向下一節點或者下一子樹的位址。
這裡有一種情況值得注意:
typedef struct s_ref ;
這個結構體型別定義是為了定義型別名s_ref,但卻失敗了。因為結構體中就引用了結構型別名,而此時還沒定義型別名。
可以改為如下:
typedef struct s_ref_ts_ref ;
這裡將執行良好。
結構體巢狀結構體名
結構體巢狀結構體名 前一段時間在看ddk中例子的時候,看到這樣的的結構體定義 typedef struct common device data common device data,pcommon device data typedef struct pdo device data pdo dev...
結構體巢狀結構體 C語言結構體
希望今年夏天的遺憾能成為你秋天的驚喜。網易雲熱評 一 結構體概念 可以簡單理解為把不同資料型別放到一起的陣列 二 結構體宣告與初始化 1 先宣告結構體型別再定義變數 2 同時定義變數 3 直接定義結構體型別變數 include include include include struct aiyou...
巢狀結構體案例
這個案例還是有很多地方可以學習的,決定記錄一下 參考 黑馬程式設計師匠心之作 c 教程從0到1入門程式設計 include include include include using namespace std 定義結構體 struct student struct teacher 賦值函式 voi...