C 语言中二维数组的退化

目录

[1. 一维数组的退化](#1. 一维数组的退化)

2.字符串数组的退化

[3. 二维数组的退化](#3. 二维数组的退化)

[3.1 为什么退化为 int (*)4 而不是 int **?](#3.1 为什么退化为 int (*)[4] 而不是 int **?)

3.2举例说明

[3.3 .总结](#3.3 .总结)


在 C 语言中,数组名在大多数情况下会退化为指向其第一个元素的指针,这种机制称为数组退化(Array Decay)。不过,这种退化的具体表现取决于数组的维度。详细解释如下:

1. 一维数组的退化

当一维数组作为参数传递给函数时,数组名退化为指向数组第一个元素的指针。

objectivec 复制代码
void func(int *arr) {
    // arr 是指向 int 的指针
}

int main() {
    int arr[5] = {1, 2, 3, 4, 5};
    func(arr); // arr 退化为 &arr[0],即指向第一个元素的指针
    return 0;
}

内存布局

假设 arr[5] 的首地址为 0x1000:arr 退化为指向 arr[0] 的指针,即 int *,指向地址 0x1000。

2.字符串数组的退化

当字符串数组(例如 char *array[])作为参数传递给函数时,它会退化为一个指向指针的指针(char **)。这是因为数组名在函数调用时会退化为一个指针,具体过程如下:

作为函数参数时的退化:

1.array 作为参数传递时,它不会直接传递整个数组,而是退化为指向数组首元素的指针。

2.因为数组的每个元素是一个 char *,所以退化后的类型是 char **,表示一个指向字符串指针的指针。

objectivec 复制代码
void processArray(char **arr, int size);
void processArray(char *arr[], int size);

使用 char *arr[] 和 char **arr 作为函数参数是等效的

3. 二维数组的退化

二维数组的退化稍微复杂一些。**当二维数组作为参数传递给函数时,它退化为指向第一行的指针。**由于每一行本身是一个一维数组,结果是一个指向数组的指针。

objectivec 复制代码
void func(int arr[][4]) {
    // arr 是指向包含 4 个 int 的数组的指针,即 int (*)[4]
}

int main() {
    int arr[3][4] = {
        {1, 2, 3, 4},
        {5, 6, 7, 8},
        {9, 10, 11, 12}
    };
    func(arr); // arr 退化为指向 arr[0] 的指针
    return 0;
}

内存布局

假设二维数组 arr[3][4] 的首地址为 0x1000:

arr 退化为指向 arr[0] 的指针,即 int (*)[4],指向地址 0x1000。

arr[0] 是一维数组,包含 4 个 int,每行占用 4 * sizeof(int) 的空间。

3.1 为什么退化为 int (*)4 而不是 int **?

二维数组是连续分布的:在内存中,二维数组是一个大的连续内存块。

int ** 表示一个指针的指针 ,通常用来表示一组独立的指针(比如动态分配的二维数组),但这里 arr 是一个连续的内存块,无法用 int ** 访问。

退化为 int (*)[4] 后,编译器知道每行占用 4 * sizeof(int) 的空间,因此可以正确地解析 arr[i][j]。

3.2举例说明

在函数中:

objectivec 复制代码
void process2DArray(char arr[][10], int rows);

这里的 arr 是一个指向数组的指针(char (*)[10]),通过 arr[i] 访问每一行。编译器知道每行是一个长度为 10 的数组,因此可以正确解析 arr[i][j]。

如果改为:

objectivec 复制代码
void process2DArray(char **arr, int rows);

这会导致类型不匹配,因为 char ** 不包含关于行长度的信息,无法正确解析 arr[i][j]。

3.3 .总结

1.数组名退化为指针的原因在于函数调用时无法直接传递整个数组。

2.对于二维数组,退化为指向行的指针 (char (*)[10]),以便编译器知道行的大小。

3.二维数组与指针数组(char **)有本质不同,因为二维数组是一个连续的内存块,而指针数组是独立的指针集合。

相关推荐
小雉系统16 小时前
BcoreOS安全通信架构:FsSession 抗算法后门安全设计
算法·安全·架构
§ꦿCFོ༉17 小时前
嵌入式八股文—C语言入门学习(四)
c语言·开发语言·学习
投图匠17 小时前
十种不同风格的 CTP接口 框架
开发语言·python
Pniubi19 小时前
关于算法用现成数据结构和手撕
数据结构
唐墨12320 小时前
linux kernel 比较数据大小的宏定义
linux·算法
爱笑的k1121 小时前
nano-vllm 源码剖析:千行 Python 手写离线推理引擎的调度、显存与并行时序
开发语言·python·vllm
拂拉氏21 小时前
【知识讲解-题目讲解】 统计满足K约束的子字符串数量2 (滑动窗口+前缀和+二分查找+分析)
算法·前缀和·二分查找·滑动窗口
X1A0RAN1 天前
PPT 图片批量处理教程:导出全部幻灯片 · 提取全部素材
开发语言·javascript·powerpoint
熊猫钓鱼>_>1 天前
普通用户视角的端侧智能体验手记【鸿蒙心迹】
开发语言·人工智能·华为·智能手机·性能优化·ai编程·harmonyos