在C++中,数组和指针经常一起出现,但它们在内存中的角色并不相同。数组是一段连续的内存空间,用来存放相同类型的多个元素;指针是一个变量,里面保存的是某个内存地址。理解它们的关系,关键在于看清数据在内存里怎么摆、地址怎么走。

数组在内存中的布局
声明一个数组后,编译器会分配一块连续的存储空间。例如 int arr[3] 会分配三个连续的 int 空间,数组名 arr 在多数表达式里会转换为指向首元素的指针,但它本身不是指针变量,不能重新赋值。
示例:查看数组地址
#include <iostream>
using namespace std;
int main() {
int arr[3] = {10, 20, 30};
// 数组首元素地址与数组名转换出的地址相同
cout << "arr: " << arr << endl;
cout << "&arr[0]: " << &arr[0] << endl;
cout << "sizeof(arr): " << sizeof(arr) << endl; // 输出整个数组大小
return 0;
}
指针如何指向数组
指针可以保存数组首元素的地址,通过指针算术访问元素。指针变量自身占用内存,存储的是地址值,这和数组名不同。数组名在 sizeof 和取地址时保留数组属性。
用指针遍历数组
#include <iostream>
using namespace std;
int main() {
int arr[3] = {10, 20, 30};
int* p = arr; // p 保存 arr 首元素地址
for (int i = 0; i < 3; i++) {
// p + i 按 int 大小偏移
cout << *(p + i) << " ";
}
cout << endl;
return 0;
}
数组名与指针的核心差异
虽然数组名在表达式中常退化为指针,但以下情况不同:
sizeof(arr)得到数组总字节数,sizeof(p)得到指针大小&arr类型为指向数组的指针,&p类型为指向指针的指针- 数组名不能做
arr = p这样的赋值
| 对比项 | 数组 | 指针 |
|---|---|---|
| 内存 | 存数据本身 | 存地址 |
| sizeof | 整体大小 | 地址宽度 |
| 可赋值 | 否 | 是 |
函数传参时的表现
当数组作为函数参数时,会退化为指针,因此函数内无法用 sizeof 获取原数组长度。这时候传指针和传数组写法等价,但语义上都是地址传递。
#include <iostream>
using namespace std;
void print(int* p, int n) {
for (int i = 0; i < n; i++) {
cout << p[i] << " ";
}
cout << endl;
}
int main() {
int arr[3] = {1, 2, 3};
print(arr, 3); // arr 退化为 int*
return 0;
}
理清C++数组和指针的内存关系,可以避免越界、误用 sizeof 等常见错误,也能更准确地理解底层数据访问方式。