C语言中的数据类型及其转换详解
http://www.cnblogs.com/jpcflyer/archive/2012/02/16/2353447.html
1. C語言中的數(shù)據(jù)類型
C語言中的類型按其組成可以分為簡單類型和構(gòu)造類型,按是否預(yù)定義了類型名字和值集可以分為基本類型和非基本類型,按是否加了類型限定符可以分為限定類型和非限定類型。
ANSI C99標(biāo)準(zhǔn)中類型定義的BNF語法如下圖。
說明:
- typedef可以定義新數(shù)據(jù)類型,如typedef long int FOUR_BYTE_INT,即定義了和long int一樣的數(shù)據(jù)類型FOUR_BYTE_INT。
- 如果typedef時加入了類型限定符或存儲區(qū)分符,比如typedef volatile char KEYBOARD,則KEYBOARD k等價于volatile char。
- 按照一般規(guī)范,新定義的數(shù)據(jù)類型同義名需要全部大寫,以免與變量名混淆。
- 利用類型定義typedef,可以為所要表示對象指定比原數(shù)據(jù)類型更合適的名字,如typedef float SPEED。
- 利用類型定義typedef,可以提高的程序的在不同編譯器上升級的可維護性,比如有些類型在某些編譯器下沒有,只需要改變類型定義即可輕松維護。
- 類型定義typedef一般用于定義比較長或復(fù)雜的名字,如struct類型,即便于書寫,又提高了程序的可讀性。
- 類型定義typedef與預(yù)處理指令#define的區(qū)別:
- 處理時間不同:前者是編譯過程中,后者是編譯過程前;
- 處理方法不同:前者是類型替換,而后者是簡單的字符串替換,在某些情況下不適合,比如定義多個變量的地方:
-
-
- 如果是想定義兩個指針類型a,b,預(yù)處理后是int * a,b。只有a是int *,是錯誤的。
-
ANSI C99標(biāo)準(zhǔn)中規(guī)定的數(shù)據(jù)類型如下圖所示。
說明:
- 同一行類型的語義相同,即可以相互替代。
- long float類型與double相同,故在C99標(biāo)準(zhǔn)中沒有此類型。
- 部分編譯器也提供了unsigned float和unsigned double,最好不要使用,以免影響程序的可移植性。
- int默認(rèn)是signed,所以int, signed, signed int三者等價。其它unsigned的情況類似。char默認(rèn)情況不確定。
2. C語言中數(shù)據(jù)類型的長度
ANSI C99標(biāo)準(zhǔn)中定義了兩類(四個)類型修飾符:long/short和unsigned/signed。
C99標(biāo)準(zhǔn)規(guī)定,long類型不能比變通類型短,short類型不能比普通類型長。而unsigned與signed的區(qū)別在實現(xiàn)上是有無符號的區(qū)別,而是使用上是取值范圍的區(qū)別,兩者表示范圍相同,但前者全是正數(shù),后者關(guān)于0對稱。
說明:
- long/short可以修飾int,long還可以修飾double。
- unsigned/signed可以修飾int, char,不可以修飾浮點型。
- int長度是機器的字長,short int是半個字長,long int是一個或兩個字長。
- unsigned/signed長度與普通類型一樣,只是表示區(qū)間不同。
3. C語言中數(shù)據(jù)類型的轉(zhuǎn)換
類型轉(zhuǎn)換分為顯示和隱式兩種,前者比較簡單,這里只講后者。下面是C99標(biāo)準(zhǔn)中給出的各種類型對象的基本轉(zhuǎn)換規(guī)則:
- 枚舉常量:轉(zhuǎn)換成int,如超出int范圍,則轉(zhuǎn)成long int等
- 浮點類型:
- 如果轉(zhuǎn)成整類型,只保留整數(shù)部分,如果超出整類型表示范圍,則轉(zhuǎn)換錯誤;
- 如果向上轉(zhuǎn)成double/long double,值不變;
- 如果向下轉(zhuǎn)成float/double等,如果能用float/double表示,則正常,如果超出表示范圍,則轉(zhuǎn)換錯誤,而如果在表示范圍內(nèi),但精度降低,則要依賴于編譯器的處理了;
- 整類型:short int/char/枚舉類型/位域類型都可轉(zhuǎn)換成int,如果超出int表示范圍,則提升到unsigned int。
- 對于二元運算符中的普通算術(shù)運算轉(zhuǎn)換,C99標(biāo)準(zhǔn)給出了如下圖所示的轉(zhuǎn)換規(guī)則:
?
說明:
- 對于unsigned char和unsigned short int的整型提升問題,C99標(biāo)準(zhǔn)給出“保值”的轉(zhuǎn)換方法:方法是將unsigned char和unsigned short int轉(zhuǎn)換成int,如果超出表示范圍,則轉(zhuǎn)成unsigned int。
- 對于表格中第五行,long int與unsigned int的情況,在vc6.0沒有這樣實現(xiàn),是直接轉(zhuǎn)成unsigned int。
4. 測試練習(xí)
1 char a = 0xb6; 2 short b = 0xb600; 3 int c = 0xb6000000; 4 5 if ( a == 0xb6) puts("a"); 6 if ( b == 0xb600) puts("b"); 7 if ( c == 0xb6000000) puts("c");答案:
在VC或x86的gcc下,只會打印出 c ,而linux的gcc則會打印出a和c。
解釋:
char在前兩者默認(rèn)是signed char,而后者默認(rèn)是unsigned char。因此當(dāng)整型提升時,在前兩者的編譯器下,三條語句分別變成如下情況:
?
1 if ( 0xffffffb6 == 0x000000b6) puts("a"); 2 if ( 0xffffb600 == 0x0000b600) puts("b"); 3 if ( 0xb6000000 == 0xb6000000) puts("c");而在linux的gcc編譯下,則是下面的情況:
?
1 if ( 0x000000b6 == 0x000000b6) puts("a"); 2 if ( 0xffffb600 == 0x0000b600) puts("b"); 3 if ( 0xb6000000 == 0xb6000000) puts("c");總結(jié)
以上是生活随笔為你收集整理的C语言中的数据类型及其转换详解的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。