Re: [問題] static下的全域指標結構陣列該如何初始化

看板C_and_CPP作者 (高髮箍)時間11年前 (2013/07/20 03:14), 編輯推噓7(708)
留言15則, 8人參與, 最新討論串3/3 (看更多)
※ 引述《NDark (溺於黑暗)》之銘言: : ※ 引述《kikiqqp (喵食罐頭)》之銘言: : : 抱歉這個標題不太好,不過我不太清楚要怎麼描述 : : 今天我先定義了一個結構為 : : typedef struct : : { : : BYTE drv_type; : : BYTE drv_mun; : : BYTE drv_size; : : BYTE drv_vol[512]; : : } VOLFS; : : 然後再宣告一個指標 : : static VOLFS *VolFs[2]; : 因為你用c compiler所以整個事情搞得很複雜. : 你的情形下 你不熟語法, 所以回答問題還把它複雜化了 : 初值的方式就是這樣 : static VOLFS *VolFs[2] = : { : {0}, : {0} : } ; static VOLFS* VolFs[2] = { NULL, NULL }; ^^^^^^ 星星我會習慣和元素型態放在一起, 既然是兩個指標那麼就用 NULL 來初始化. 但如果你其實是想要: 1. 兩個指標都指向已經存在的結構變數 2. 被指到的結構變數每個位元組都是 0 那麼再加上兩個靜態結構變數即可: static VOLFS data[ 2 ] = { { 0, 0, 0, {0} }, { 0, 0, 0, {0} } }; static VOLFS* VolFs[2] = { &data[0], &data[1] }; 靜態結構變數陣列 data 裡元素的初始化方式稱作: aggregate initialization http://ppt.cc/A8HN 雖然 data 跟 VolFs 初始化順序是不確定的, 但是取成員位址來 初始化另一個陣列不會影響執行 main() 之後的結果. : 但這不是你要的,你要的就是另外寫一個初始化函式 : 在main的時候找機會去配置記憶體給那個陣列 : VOLFS* VOLFSInitilaize( void ) : { : VOLFS* ret = (VOLFS*)malloc( sizeof( VOLFS ) ) ; : memset( ret , 0 , sizeof( ret ) ) ; : return ret ; : } : ... : VolFs[0] = VOLFSInitilaize() ; : VolFs[1] = VOLFSInitilaize() ; : 以下是c++編譯器下類似c的做法 : 比較符合你要的在宣告時就初值好. : #include <stdio.h> : #include <stdlib.h> : #include <string.h> : typedef struct : { : char drv_type; : char drv_mun; : char drv_size; : char drv_vol[512]; : } VOLFS; : VOLFS* VOLFSInitilaize( void ) ; : static VOLFS *VolFs[2] = : { : VOLFSInitilaize(), : VOLFSInitilaize() : } ; : VOLFS* VOLFSInitilaize( void ) : { : VOLFS* ret = (VOLFS*)malloc( sizeof( VOLFS ) ) ; : memset( ret , 0 , sizeof( ret ) ) ; : return ret ; : } : 正式c++的封裝方式會像這樣 : class VOLFS : { : public : : VOLFS(void) : : drv_type( 0 ) : , drv_mun( 0 ) : , drv_size( 0 ) : { : memset( &drv_vol , 0 , sizeof( char ) * 512 ) ; ^^^^^^^^ 要搞清楚這邊的語意 : } ; : public : : char drv_type; : char drv_mun; : char drv_size; : char drv_vol[512]; : } ; : static VOLFS *VolFs[2] = : { : new VOLFS , : new VOLFS : } ; : 是不是乾淨多了? : 不過經驗上還是建議減少使用static,減少使用多維陣列, : 因為控制不好很容易出問題. 如果真的想把東西放堆積上, C++ 是這樣寫的... static VOLFS* VolFs[2] = { nullptr, nullptr }; static struct VolFsManager { VolFsManager() { for(auto& elem : VolFs) elem = new VOLFS; } ~VolFsManager() { for(auto elem : VolFs) delete elem; } } manager; int main() { for(auto elem : VolFs) assert(elem != nullptr); } 很基本, 而且比你的還乾淨... 順帶一提, VolFs 這變數命名很爛... -- ※ 發信站: 批踢踢實業坊(ptt.cc) ◆ From: 112.105.94.167 ※ 編輯: loveme00835 來自: 112.105.94.167 (07/20 03:31)

07/20 11:01, , 1F
:)
07/20 11:01, 1F

07/20 17:34, , 2F
星星黏前面有個壞處,會以為 int* ptrA, ptrB; 是對的...
07/20 17:34, 2F

07/20 18:50, , 3F
還蠻好奇為什麼連續宣告當初要弄成這樣
07/20 18:50, 3F

07/20 18:50, , 4F
是為了typedef Foo Bar,*PBar;這種東西嗎
07/20 18:50, 4F

07/20 19:17, , 5F
可能分析語法比較方便吧 int x 跟 int x[10],右邊的資料
07/20 19:17, 5F

07/20 19:18, , 6F
打錯,左邊的資料形態永遠都是直接抓出來比對就好,會有
07/20 19:18, 6F

07/20 19:18, , 7F
變形的地方一律在右邊跟識別項在一起
07/20 19:18, 7F

07/20 22:45, , 8F
這變數的確取名很爛不過前人開發如此,後人維護只能先忍受
07/20 22:45, 8F

07/21 01:27, , 9F
to xxxx9659: 那表示你要換行寫了
07/21 01:27, 9F

07/21 10:08, , 10F
很好.不過我用0不用NULL的原因是NULL也要include.
07/21 10:08, 10F

07/21 10:09, , 11F
而且NULL其實也就是定義為0.
07/21 10:09, 11F

07/21 13:08, , 12F
樓上,NULL 未必是 (void *)0, C++ 請愛用 nullptr...
07/21 13:08, 12F

07/21 14:40, , 13F
對,所以如果不include的話,那就不用.
07/21 14:40, 13F

07/21 17:27, , 14F
to kikiqqp: 表示要重構了, 你現在不中止這種惡性循環
07/21 17:27, 14F

07/21 17:28, , 15F
下一個進來的, 多維護你的 code 更慘
07/21 17:28, 15F
文章代碼(AID): #1HwP0VQN (C_and_CPP)
討論串 (同標題文章)
文章代碼(AID): #1HwP0VQN (C_and_CPP)