2011-12-20 64 views
0

我最近整合了兩個在不同硬件體系結構上運行的應用程序,其中出現的問題包括網絡字節排序問題和結構填充問題。位字段和編譯指示

兩人都是很容易解決 - 用於填充具體而言,我不得不在我的網絡結構中添加編譯指示像這樣:

#pragma pack(1) 
struct {}; 
#pragma pack(0) 

我看見有幾個與位域的問題,昨天,雖然我有沒用過。我想知道...通過使用位域定義結構來嘗試停止填充會更合適嗎?這在這種情況下會有所幫助嗎?

此外,我還沒有在C++代碼中遇到過很多bitfields - 它們更像是一個C函數,它沒有被使用太多,或者只是碰巧在不使用它們的代碼上工作?

+0

你只是沒有碰巧在使用位域的代碼上工作。 **在適當的地方非常有用**。他們適當的地方雖然很少,但具體。 –

回答

3

不,位域是外部表示(如網絡數據包定義)的可怕選擇。完全取決於編譯器選擇位域內存中的佈局(以何種方式排序位,爲給定字段預留多少字節,等等),因此絕對會干擾互操作性。

這就是說,我反對使用「裸」結構,因爲你遇到了這個問題。

在我看來,正確的方法是手動逐個序列化/反序列化字段。

+0

是的,我們的大多數接口都使用某種序列化格式(儘管我們選擇了令人驚訝的不方便的)。這個界面並不是絕對更有問題,所以我現在看到了更多的好處。 –

+1

要添加到答案:'#pragma pack'是一個附註,這意味着它可能不會出現在所有機器上,並且可移植代碼不能依賴它。更重要的原因是不使用裸結構(甚至是「int」,因爲int的大小和表示形式可能因機器而異)。 –