中文字幕av专区_日韩电影在线播放_精品国产精品久久一区免费式_av在线免费观看网站

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

淺談C語言中聯合體

發布時間:2020-07-17 10:38:22 來源:億速云 閱讀:190 作者:小豬 欄目:編程語言

小編這次要給大家分享的是淺談C語言中聯合體,文章內容豐富,感興趣的小伙伴可以來了解一下,希望大家閱讀完這篇文章之后能夠有所收獲。

      當多個數據需要共享內存或者多個數據每次只取其一時,可以利用聯合體(union)。在C Programming Language 一書中對于聯合體是這么描述的:

     1)聯合體是一個結構;

     2)它的所有成員相對于基地址的偏移量都為0;

     3)此結構空間要大到足夠容納最"寬"的成員;

     4)其對齊方式要適合其中所有的成員;

下面解釋這四條描述:

     由于聯合體中的所有成員是共享一段內存的,因此每個成員的存放首地址相對于于聯合體變量的基地址的偏移量為0,即所有成員的首地址都是一樣的。為了使得所有成員能夠共享一段內存,因此該空間必須足夠容納這些成員中最寬的成員。對于這句“對齊方式要適合其中所有的成員”是指其必須符合所有成員的自身對齊方式。

下面舉例說明:

如聯合體

union U
{
 char s[9];
 int n;
 double d;
};

s占9字節,n占4字節,d占8字節,因此其至少需9字節的空間。然而其實際大小并不是9,用運算符sizeof測試其大小為16.這是因為這里存在字節對齊的問題,9既不能被4整除,也不能被8整除。因此補充字節到16,這樣就符合所有成員的自身對齊了。從這里可以看出聯合體所占的空間不僅取決于最寬成員,還跟所有成員有關系,即其大小必須滿足兩個條件:

1)大小足夠容納最寬的成員;

2)大小能被其包含的所有基本數據類型的大小所整除。

測試程序:

/*測試聯合體 2011.10.3*/

#include <iostream>
using namespace std;

union U1
{
 char s[9];
 int n;
 double d;
};

union U2
{
 char s[5];
 int n;
 double d;
};

int main(int argc, char *argv[])
{
 U1 u1;
 U2 u2;
 printf("%d\n",sizeof(u1));
 printf("%d\n",sizeof(u2));
 printf("0x%x\n",&u1);
 printf("0x%x\n",&u1.s);
 printf("0x%x\n",&u1.n);
 printf("0x%x\n",&u1.d);
 u1.n=1;
 printf("%d\n",u1.s[0]);
 printf("%lf\n",u1.d);
 unsigned char *p=(unsigned char *)&u1;
 printf("%d\n",*p);
 printf("%d\n",*(p+1));
 printf("%d\n",*(p+2));
 printf("%d\n",*(p+3));
 printf("%d\n",*(p+4));
 printf("%d\n",*(p+5));
 printf("%d\n",*(p+6));
 printf("%d\n",*(p+7));
 return 0;
}

輸出結果為:

16
8
0x22ff60
0x22ff60
0x22ff60
0x22ff60
1
0.000000
1
0
0
0
48
204
64
0

對于sizeof(u1)=16。因為u1中s占9字節,n占4字節,d占8字節,因此至少需要9字節。其包含的基本數據類型為char,int,double分別占1,4,8字節,為了使u1所占空間的大小能被1,4,8整除,則需填充字節以到16,因此sizeof(u1)=16.

對于sizeof(u2)=8。因為u2中s占5字節,n占4字節,d占8字節,因此至少需要8字節。其包含的基本數據類型為char,int,double分別占1,4,8字節,為了使u2所占空間的大小能被1,4,8整除,不需填充字節,因為8本身就能滿足要求。因此sizeof(u2)=8。

從打印出的每個成員的基地址可以看出,聯合體中每個成員的基地址都相同,等于聯合體變量的首地址。

對u1.n=1,將u1的n賦值為1后,則該段內存的前4個字節存儲的數據為00000001 00000000 00000000 00000000

因此取s[0]的數據表示取第一個單元的數據,其整型值為1,所以打印出的結果為1.

至于打印出的d為0.000000愿意如下。由于已知該段內存前4字節的單元存儲的數據為00000001 00000000 00000000 00000000,從上面打印結果48,204,64,0可以知道后面4個字節單元中的數據為00110000 11001100 01000000 00000000,因此其表示的二進 制浮點數為

00000000 01000000 11001100 00110000 00000000 00000000 00000000 00000001

對于double型數據,第63位0為符號位,62-52 00000000100為階碼,0000 11001100 00110000 00000000 00000000 00000000 00000001為尾數,根據其值知道尾數值約為0,而階碼為4-1023=-1019,因此其表示的浮點數為1.0*2^(-1019)=0.00000000000......,因此輸出結果為0.000000。

看完這篇關于淺談C語言中聯合體的文章,如果覺得文章內容寫得不錯的話,可以把它分享出去給更多人看到。

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

怀远县| 金乡县| 丰原市| 东兰县| 辽阳市| 南涧| 贡山| 犍为县| 襄垣县| 锦屏县| 新余市| 定日县| 上虞市| 自治县| 乾安县| 汉川市| 山阳县| 响水县| 浦北县| 文山县| 嘉峪关市| 雅江县| 陈巴尔虎旗| 达孜县| 台东市| 泾川县| 同心县| 北海市| 当阳市| 长春市| 阿巴嘎旗| 紫云| 平远县| 兰考县| 藁城市| 巴林左旗| 黔南| 灵宝市| 婺源县| 宣武区| 札达县|