6

c语言入门19,应该没有人故意写不可移植的代码吧,C语言的数据类型介绍

 3 years ago
source link: https://blog.popkx.com/introduction-to-c-language-19-nobody-should-intentionally-write-non-transplantable-code-the-data-type-of-c-language-is-introduce/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

还记得在《》一节中,我们提到 C 语言定义了不同的数据类型吗?不同数据类型使得 C 语言更加灵活,解决问题时,选择合适的数据类型,能够大大提升程序最终的效率。本节,我们再细说说 C 语言的数据类型。

bbdff344bb2d1fe6e9f14ab8aece9a86.png

C 语言中的数据类型

计算机存储的最小单位是字节(Byte),一个字节通常是 8 个 bit。我们常说的硬盘容量 500GB,就是指硬盘能够存储 500G 字节的数据。C 语言规定 char 型占一个字节的存储空间,如果是 unsigned char(无符号),则可表示的取值范围是 0~255。如果是 signed char(有符号),则取值范围为 -128~127。

定义 char 型变量时不指定 unsigned 或 signed ,C标准规定这种情况属于 implemention defined,具体 char 型变量是否有符号取决于使用的编译器。C 标准的原则是:优先考虑效率,可移植性其次。所以如果在对应的体系架构上,char 型变量有符号时效率最高,则编译器就将其解释为有符号。若char 型变量无符号时效率最高,则编译器就将其解释为无符号。

应该没有人故意写出没有移植性的代码,所以建议写 C 语言代码用到 char 型变量时,显性的指出其是否有符号。

a6cd1ef4134fbe94e6d5d027c84c5a39.png

另外,整型数据类型还有 short int(可简写为 short),int, long int(可简写为 long),long long int(可简写为 long long)几种,这些类型也可以加上 unsigned 或 signed 表示无符号型或有符号型,与 char 类型的区别主要在于占用的存储空间不同,究竟这几种整型类型占几个字节,C 标准没有规定,所以在不同架构的计算机中,这几种类型占用的空间可能不同。例如在大多数 32 位计算机中,这几种数据类型占用的字节数分别为 2,4,4,8。而在大多数 64 位计算机中,这几种数据类型占用的字节数分别为 2,4,8,8。

除了 char,其他几种整型类型如果定义时没有写符号,则默认为是有符号的。

C 标准规定的浮点型有 float,double,long double,但是对每种数据类型占用的存储空间却没有规定。浮点型的实现在不同的平台上的差异性比整型更大。有的处理器自带的有浮点运算单元,称为浮点运算的硬件实现。有的处理器没有,只能用整型运算模拟,这称为浮点运算的软件实现

5ad5dd04f4b49a9144dc3d935322b7ce.png

C 语言定义了这么多的数据类型,我们在 C 语言编程时应选择最合适的数据类型。例如某个变量的变化范围是 0~100,那选择 char 类型就足够了(无论有没有符号),选择 long 类型会导致性能下降,原因我们在之前的文章里已经解释过了。如果某个变量的变化范围可能超过 255,那就不能选择 char 类型了,否则会造成数据溢出,例如

unsigned char i = 255;
i = i + 2;
printf("i=%d\n", i);

以上代码会输出“i=1”。

776ea61ff419148c3f1f2a1c352de866.png

C 语言的数据类型转换

C 语言中的基本运算,如+-* /%这些算术运算以及> < >= <= == !=这些比较运算,都需要两边的数据类型一致,如果不一致,会自动转换为一致的类型。例如:

unsigned char a = 254, b = 3;
int sum = a+b;

计算 sum 之前,会先把 a 和 b 提升为 int 类型再相加。

C语言的数据类型自动转换,一般都是转为占用字节数较多的类型,如果有浮点型,则优先转为浮点型。例如,如果有一边的类型为 long double,则把另一边也转为 long double;否则,如果有一边为 double 类型,则把另一边也转为 double 类型;否则,如果有一边为 float,则把另一边也转为 float 类型;。。。接着就是整型了,也是依次按照 long long -> long -> int -> short -> char 的顺序转换类型的。

66be153bdc808c4675d593ee347e20bd.png

C 语言在赋值时,也会做自动的类型转换,例如:

int i = 3.14;
printf("i=%d\n", i);

以上代码会输出 “i=3”,i 只保留的 3.14 的整数部分。

C 语言还有强制类型转换,只需要在要转换的数据前加上 (要转换的类型),例如:

int i = 257;
unsigned char j = (unsigned char)i;
printf("j=%d\n", j);

以上代码会输出“j=1”,溢出的部分被忽略了。

8399ebcf80ef585ae762e70810db7682.png

初学者看到这些规则通常会很不舒服,觉得这不是在学编程而是在啃法律条文,结果越学越泄气。是的,C语言并不像一个数学定理那样完美,现实世界里的东西总是不够完美的。但还好啦,C程序员已经很幸福了,只要严格遵照C标准来写代码,不要去触碰那些阴暗角落,写出来的代码就有很好的可移植性。想想那些可怜的JavaScript程序员吧,他们甚至连一个可以遵照的标准都没有,一个浏览器一个样,因而不得不为每一种浏览器的每一个版本分别写不同的代码。


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK