C/C++静态数组与动态数组的区别
2024-10-18 18:25:03
简介
以下三行代码有什么区别?
int a[10];
int *a = (int*)malloc(sizeof(int)*10);
int *a = new int[10];
- 第一行代码定义a为包含10个int类型元素的整形数组。
- 第二行和第三行分别使用的是C和C++来定义动态数组,他们的结果是相同的。a都可以表示为一个动态数组。
我们可以使用a[1]来取数组a的第1个元素。那他们有什么区别呢?
解释
我们从指针开始说起。所谓指针,就是用来存放内存地址的一个变量,首先,指针是个变量;其次,指针存放的是内存地址。
指针的定义中包含了一个重要的说明:指针中存放的内存地址处的内容应该如何解析。例如:int *a;
说明a
是一个指针,他存放的地址处的数据被解析为一系列连续的int
型数据。
那int a[10]
,可以说明a
是一个指针么?其实,这样说是不准确的。a
其实本身就是一个内存地址。只是我们在实际运行之前并不知道他真正代表哪个地址。就像宏在编译的时候被替换成宏定义的内容,静态数组a
实际上在执行的时候是被替换成真实的内存地址的。也就是说a
已经是内存地址了,不是变量。
那么对于int a[10]
和 int *b = new int[10]
,a[2]
和b[2]
有什么区别呢?
a[2]
,b[2]
在赋值符号=
的右端的时候。此时表示取a[2]
和b[2]
的值。对于a[2]
,首先a
代表的是个内存地址,在这个内存地址处偏移sizeof(int)*2
个字节,取连续sizeof(int)
个字节,并将其解析为int
类型的数。对于b[2]
,首先b
是一个指针,其值是一个内存地址,首先b
这个变量在内存中的地址被找到,然后取连续的sizeof(int*)
个字节,解析为一个内存地址,然后在这个地址处偏移sizeof(int)*2
个字节,取连续sizeof(int)
个字节,并将其解析为int
类型的数。a[2]
,b[2]
在赋值符号=
的左端的时候。表示向相应的内存位置赋值。赋值符号右端的表达式的结果不管是什么类型的值,都会被默认强制类型转化为int
型数据。对于a[2]
,a
代表的是个内存地址,在这个内存地址处偏移sizeof(int)*2
个字节,向连续的sizeof(int)
个字节内存中写入赋值号右端的结果。对于b[2]
,首先b
这个变量在内存中的地址被找到,然后取连续的sizeof(int*)
个字节,解析为一个内存地址,然后在这个地址处偏移sizeof(int)*2
个字节之后,向连续的sizeof(int)
个字节内存中写入赋值号右端的结果。
实验
试验下前面讨论的内容:
#include <stdio.h>
#include <stdlib.h>
#include <inttypes.h>
int main(int argc, char** argv){
int a[10];
printf("%.16X\n", (uint64_t)(&a));
printf("%.16X\n", (uint64_t)(a));
int *b = new int[10];
printf("%.16X\n", (uint64_t)(&b));
printf("%.16X\n", (uint64_t)(b));
delete[] b; b = NULL;
return EXIT_SUCCESS;
}
某次执行结果:
000000003093F838
000000003093F838
000000003093F878
00000000309A8D90
根据输出结果,可以推断,a
和&a
的值是相同的,说明a
已经是地址了,取地址后还是原先的地址,所以两次地址是一样的。
后两次输出结果不同,是应为b
是一个指针,是变量,变量的地址与他存储的内存地址是不同的。
最新文章
- AlloyTeam2015前端大会都说了啥
- OpenGL EXT: shader_buffer_load
- 初识MariaDB存储引擎
- TCP/IP详解学习笔记(8)-- UDP:用户数据报协议
- prototype原型模式中的问题
- [反汇编练习] 160个CrackMe之026
- wikioi 1010 过河卒
- Linux下生产者与消费者的线程实现
- 区段extent及数据块
- spark MLLib的基础统计部分学习
- OPENCV形态学操作1
- Java基础--面向对象编程3(继承)
- 轻型Database- sqlite入门
- 工程师的URL大全
- 使用 logrotate 清理日志
- 《Linux就该这么学》第十三天课程
- xx系统属性分析
- ssl证书部署问题
- springBoot基础2
- Linux - find 查找
热门文章
- SpringBoot(五):@ConfigurationProperties配置参数绑定
- read运行
- Spring boot 整合 Mybatis (完整版)
- java中lamda表达式的应用
- jq跨域获取json
- [LeetCode] Daily Temperatures 日常温度
- “百度杯”CTF比赛 九月场_YeserCMS
- 【实验吧】CTF_Web_因缺思汀的绕过
- pytorch 移动端框架 thnets 附c示例代码
- hdu 5607 BestCoder Round #68 (矩阵快速幂)