2010-09-30 16 views
-1

語言:C++如何在char *中打包結構的必需位?

我的工作位緊縮(從給定的數據中提取所需要的比特,並在一個char *包裝它們)。我的代碼目前支持: - 整數 - 人物 - 字符串

現在,如果我必須存儲的結構所需的位,我應該怎麼做呢?我的意思是我應該期望作爲廣義代碼w.r.t結構的輸入參數?

這個問題可能是模糊的,我不期待直接的答案,甚至提示和指針,讚賞。

回答

2

看看this是一個非常緊湊的格式,或者使用標準的編組格式,比如json,xml,boost序列化等等,並且保存你自己的白髮。

+0

謝謝您提供的信息鏈接。如果我覺得沒有其他方法可以做到這一點,最終會考慮使用外部庫的選項。 – 2010-09-30 09:29:09

+0

你不應該(等到沒有別的辦法了)。除了學習如何去做,你自己寫一個圖書館的理由很少,特別是當你不熟悉這個領域的時候。所以考慮外部庫應該是第一件要做的事情,編寫自己應該是​​最後的選擇,特別是對於如此複雜的基本組件(Just IMVHO) – 2010-09-30 10:40:25

+0

我剛剛發現** bitmagic **庫:http://bmagic.sourceforge。淨/這可以用於上述問題?它有什麼嚴重的限制嗎? – 2010-10-01 07:58:58

0

正如piotr已經建議:嘗試使用現有的庫來編組。

但是,因爲你已經在做了自己:
如果你支持的原語表示的是字節,那麼你不應該是位緊縮(有可能是有關術語有些混亂),否則可以考慮使用std::bitset
因爲C++不支持reflection,所以C++沒有幫助以通用,安全和便攜的方式使用字節包結構,因此準備爲每個基元和每個成員結構打包一個函數。
重載確實有助於以通用方式調用這些函數,因此容器(vector ...)的打包可以一般地完成。但是,如果您想要這樣做,那麼首選免費函數而不是成員函數,以避免在打包原語和打包結構之間出現差異。

例子:

void Pack(const MyStruct& str, Packer& pack) 
{ 
    Pack(str.int1, pack); 
    Pack(str.string1, pack); 
    Pack(str.otherStruct, pack); 
} 
+0

感謝您的詳細回覆。我不是以英語爲母語的人。請解釋「支持原語」在這裏的含義。正如你所說:「所以要準備好爲每個結構編寫一個函數來打包每個基元和每個成員結構。」這是不可行的,因爲我的國際海事組織,因爲我的這個位封裝功能應該處理任何類型的結構不只是一個! – 2010-09-30 09:30:52

+0

我只是在檢查「bitset」的作用。感謝您的信息。 – 2010-09-30 09:33:50

+0

@anishakaul:你提到你的實現已經支持整數,字符和字符串。這些是受支持的基元。不支持的基元包括雙打,布爾,...結構和容器(嚴格來說也是字符串)是由基元組成的化合物。 – stefaanv 2010-09-30 09:43:29

0

您可以使用reinterpret_cast<char*>()訪問結構,就好像是一個char*

#include <iostream> 
using namespace std; 

struct myStruct 
{ 
    char a; int b; 
}; 

int main(int argc, char* argv[]) 
{ 
    myStruct instance = { 10, 100 }; 

    //Treat the myStruct instance as though it were a char* 
    char* pchar = reinterpret_cast<char*>(&instance); 

    //Output the values of the bytes to the console 
    for(int i = 0; i < sizeof(instance); i++) 
     cout << (int)pchar[i] << endl; 

    getchar(); 
    return 0; 
} 

但是請注意,因爲排列的,不是所有的字符的意志包含有意義的數據至少在視覺工作室中,這可以使用pack編譯指示來固定,但結果仍然是高度依賴於體系結構/編譯器的。

因此,如果你想收拾字節的方式,是所有便攜式/維護(即你要在現實世界中使用這個),我會高度建議使用piotr提到的序列化方法之一。