C语言中各种整型变量在不同字长机器上的字节数详细探讨

本文探讨了C/C++中short、int及long类型的字节长度差异,特别是在不同位数的操作系统和编译器环境下它们的变化。指出int在64位系统中仍保持32位长度,强调了使用sizeof确定类型大小的重要性。

今天,看到一个特别基础的问题探讨,但是认识比较深入,感觉文章比较好,转载至此 文末附上原文链接

突然间就想到了longint到底什么区别(发现有很多问题都是突然间想到的),然后百度、google各种查找,各种书籍:《C++ Primer》、《C程序设计语言》查看,终于明白了一些。下面的话选自《C程序设计语言》:

shortlong两个限定符的引入可以为我们提供满足实际需要的不同长度的整形数。int通常代表特定机器中证书的自然长度。short类型通常为16位,long类型通常为32位,int类型可以为16位或32位。各编译器可以根据硬件特性自主选择合适的类型长度,但要遵循下列限制:shortint类型至少为16位,long类型至少为32位,并且short类型不得长于int类型,而int类型不得长于long类型。

下面一段话选自《C++ Primer》:

shortintlong类型都表示整型值,存储空间的大小不同。一般,short类型为半个机器字长(word)长,int类型为一个机器字长,而long类型为一个或两个机器字长(在32位机器中int类型和long类型通常字长是相同的)。

这时候我又想到了,不同的机器位下,这三个类型到底有什么区别,short就不说了,从上面两段介绍来说,short应该都是16位了,那么intlong呢?百度一下(我不喜欢百度,但是google不稳定,只能百度了)。先看列表:

类型

16位系统/字节

32位系统/字节

64位系统/字节

char

1

1

1

char*

2

4

8

short

2

2

2

int

2

4

4

long

4

4

8

long long

8

8

8

从表中可以看出这么几个问题,int类型在64位系统下竟然是4个字节32位的。还有,这些玩意儿到底跟什么有关系?是谁在控制着?从网上扒了各种解释,大概有这么两点:

164位系统下,编译器为了向前兼容,将int类型自动编译为4个字节的了;

2、这些个玩意儿就是编译器来控制的,不同的编译器将int类型编译成不同长度的,所以,使用什么编译器才是重要的,比如:32位系统,tc下的int就是16位长度的,VC就是32位长度的。

3、long long是标准的8 bytes,不受编译器限制,所以,16位的依然也是8 bytes。(多谢博友0_0i_i 的指正

通过上面的介绍,应该大致明白整型的定义了吧,所以我们在使用整型变量的时候还是得小心的,尤其需要其所占空间长度的时候,千万不要想当然的认为int32位系统下就是4个字节。尽量使用sizeof取值


原文链接  http://blog.sina.com.cn/s/blog_6f62c9510101svjz.html

<think>好的,我现在需要回答用户关于C语言基本数据类型不同字长CPU架构下的内存占用情况的问题。用户特别提到了8位和其他不同字长的架构,比如32位、64位等。首先,我需要回忆C语言标准中对数据类型的规定,以及不同架构和编译器的影响。 根据C标准,像short、int、long这样的整数类型的大小并没有严格规定,而是由编译器和目标架构决定的。例如,short通常至少是16位,int至少是16位,并且不小于short。long至少是32位,而long long是64位。不过,这些只是最小值,实际大小可能因平台而异。 接下来,我需要参考用户提供的引用内容。引用[2]提到,字节通常是8位,而字长与架构相关,如32位机的字长是4字节,64位机是8字节。引用[4]指出,int的长度不仅与CPU架构有关,还与编译器有关,遵循C/C++规定,int字长机器字长相同,但编译器根据操作系统字长来定义。这可能意味着在8位架构中,int可能被定义为16位,但需要确认。 用户之前的问题是关于8位架构的特点,例如数据总线为8位,地址总线可能更宽。在8位架构中,处理器的字长是8位,但通常编译器可能会将int设为16位,因为处理8位可能效率不高,或者为了满足C标准的最小要求(int至少16位)。例如,在Arduino(基于8位AVR)中,int是16位,而char是8位。 对于其他架构,比如16位(如早期的8086)、32位(x86)、64位(x86_64),数据类型大小会变化。例如,在32位系统中,int通常是32位,而在64位系统中,可能仍然是32位,而long可能变成64位,这取决于数据模型(如LP64)。 用户还提到不同数据模型的影响,比如ILP32、LP64等。需要解释这些模型如何影响类型的大小。例如,在LP64中,long和指针是64位,而int是32位。这可能在不同系统中导致差异。 需要结合用户提供的引用,特别是引用[4]中提到的int长度与编译器、操作系统和CPU架构的关系。例如,在8位架构中,虽然CPU是8位,但编译器可能将int设为16位,以符合C标准的最小要求,或者根据操作系统字长(如果有的话)。 然后,需要整理出不同架构下的典型数据类型大小,可能包括8位、16位、32位、64位架构,以及常见的数据模型(如ILP32、LP64)。例如,在8位架构中,short可能是16位,int可能是16位,long可能是32位。在32位架构的ILP32模型中,int、long和指针都是32位,而LP64中long和指针是64位,int是32位。 还需要注意用户提到的嵌入式系统中使用较小的类型(如short)来节省资源,如引用[3]中提到嵌入式系统中使用short以减少内存占用。这可能影响编译器在8位架构中选择较小的类型,但根据标准,short至少是16位,所以即使是在8位系统中,short仍可能占用2字节。 最后,总结出不同架构下的数据类型大小,并指出影响这些大小的因素,如编译器、数据模型等。同时,提供验证方法,如使用sizeof运算符或查看limits.h头文件,如引用[4]中的示例代码。</think>#### C语言基本数据类型不同字长CPU架构中的内存占用分析 在C语言中,基本数据类型的内存占用受**CPU字长**、**编译器实现**和**数据模型**共同影响。以下是不同字长架构下的典型内存分配规律(以主流编译器为例): --- ### 一、核心规则 1. **C语言标准的最低要求** - `char`: $1$字节($8$位) - `short`: $\geq 2$字节($\geq 16$位) - `int`: $\geq 2$字节($\geq 16$位,且$\geq \text{short}$) - `long`: $\geq 4$字节($\geq 32$位) - `long long`: $8$字节($64$位,C99标准)[^3] 2. **数据模型决定具体大小** - **ILP32**(32位系统常见): `int`、`long`、指针均为$4$字节 - **LP64**(64位系统主流): `long`、指针为$8$字节,`int`为$4$字节 - **其他模型**:如`ILP64`(较少见,`int`也为$8$字节) --- ### 二、不同字长架构下的典型内存占用 | 数据类型 | 8位架构(如AVR) | 16位架构(如8086) | 32位架构(ILP32) | 64位架构(LP64) | |---------------|-------------------|---------------------|--------------------|-------------------| | `char` | $1$字节 | $1$字节 | $1$字节 | $1$字节 | | `short` | $2$字节 | $2$字节 | $2$字节 | $2$字节 | | `int` | $2$字节[^1] | $2$字节 | $4$字节 | $4$字节 | | `long` | $4$字节 | $4$字节 | $4$字节 | $8$字节 | | `long long` | $8$字节 | $8$字节 | $8$字节 | $8$字节 | | 指针(`void*`)| $2$~$3$字节[^2] | $2$~$4$字节 | $4$字节 | $8$字节 | #### 说明: 1. **8位架构**(如AVR微控制器) - `int`通常为$2$字节,因CPU字长为$8$位,但需满足C标准最小值($16$位)[^1]。 - 指针大小取决于地址总线宽度(如$16$位地址总线对应$2$字节指针)[^2]。 2. **16位架构**(如早期x86) - `int`与`short`均为$2$字节,`long`为$4$字节(如Turbo C编译器)。 3. **32位架构** - 采用ILP32模型:`int`、`long`、指针均为$4$字节(如32位Linux)。 4. **64位架构** - 主流LP64模型:`long`与指针为$8$字节,`int`保持$4$字节(如64位Linux/macOS)。 --- ### 三、验证方法与注意事项 1. **直接验证** 使用`sizeof`运算符或`<limits.h>`头文件: ```c printf("short大小: %zu字节\n", sizeof(short)); // 输出示例:2 printf("INT_MAX: %d\n", INT_MAX); // 输出示例:32767(16位int) ``` 2. **跨平台开发建议** - 优先使用`<stdint.h>`中的精确宽度类型(如`int16_t`、`uint32_t`)[^3]。 - 避免依赖`int`的隐式大小,如嵌入式开发中显式指定`uint8_t`节省内存。 --- ### 四、典型应用场景 - **8位嵌入式系统**:使用`uint8_t`(1字节)优化存储,如传感器数据采集[^3]。 - **64位高性能计算**:利用`long`(8字节)处理大整数,避免溢出[^3]。 - **跨平台通信协议**:固定宽度类型(如`int32_t`)确保数据兼容性。 --- ### 相关问题 1. 为什么64位系统中`int`类型仍为4字节? 2. 如何避免不同架构下的整数溢出问题? 3. 嵌入式系统中如何优化数据类型的存储效率? --- [^1]: 8位架构的编译器通常将`int`设为16位以满足C标准最低要求,尽管CPU字长为8位。 [^2]: 地址总线宽度决定指针大小(如16位地址总线对应2字节指针)。 [^3]: 精确宽度类型(如`int16_t`)可显式控制内存占用,适配不同硬件需求。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值