-ciox.jpg)
【C】数组和指针
AI-摘要
Tianli GPT
AI初始化中...
介绍自己
生成本文简介
推荐相关文章
前往主页
前往tianli博客
数组和指针
1.1 数组和指针关系
数组名是操作当前数组对应的名称,同时数组名是【指针常量】,存储当前数组在内存中的空间首地址。
1.2 案例代码
#include <stdio.h>
int main(int argc, char const *argv[])
{
int arr[10] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
/*
数组名是一个指针常量
*/
printf("arr = %p\n", arr);
/*
数组的内存空间首地址,同时也是数组中下标为 0 的元素内存
空间首地址。
*/
printf("&arr[0] = %p\n", &arr[0]);
/*
当前操作得到的结果为 1,也就是数组中下标为 0 的元素数据内容
可以认为 int arr[10] 等价理解为 int *arr
*arr 根据当前 arr 指针存储的地址,访问对应的内存空间,读取
4 个字节内存,将 4 个字节中所有的二进制数据内容当做 int 类型
数据处理
*/
printf("*arr = %d\n", *arr);
/*
假设数组内存空间首地址以为 0xACB0
请问数组中下标为 6 的元素空间首地址多少
0xACB0 + 6 * 4 ==> 0xACB0 + 24
==> 0xACB0 + 0x18
==> 0xACC8
*/
printf("&arr[6] = %p\n", &arr[6]);
return 0;
}
1.3 数组下标和地址的关系
#include <stdio.h>
int main(int argc, char const *argv[])
{
int arr[10] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
printf("arr = %p\n", arr);
printf("&arr[5] = %p\n", &arr[5]);
/*
【重点】
指针加上一个整数,可以认为是当前地址数据 + n * sizeof(目标元素数据类型)
当前 arr 是一个存储数据类型为 int 类型数组,对应指针数据情况为
int *arr 目标数据类型为 int 类型
假设 arr ==> 0xACB0
arr + 4 ==> 0xACB0 + 4 * sizeof(int)
==> 0xACB0 + 4 * 4
==> 0xACB0 + 0x10
==> 0xACC0
计算得到数组中下标为 4 的元素内存空间首地址。
*/
printf("arr + 4 = %p\n", arr + 4);
/*
获取当前数组中下标为 4 的元素数据
*/
printf("*(arr + 4) = %d\n", *(arr + 4));
return 0;
}
/*
*arr + 1 = ?
*arr 取值数组中下标为 0 的元素 1
1 + 1 ==> 2
arr + 2 = ?
0xACB0 + 2 * 4 ==> 0xACB8
*(arr + 2) = ?
3
*arr + *(arr + 5) = ?
1 + 6 ==> 7
*/
1.4 地址减法
#include <stdio.h>
int main(int argc, char const *argv[])
{
int arr[10] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
/*
地址减法得到的是两个地址对应元素的个数差。
【要求】必须是同源地址。例如: 来自同一个数组,同一个结构.
*/
printf("&arr[5] - &arr[1] = %d\n", &arr[5] - &arr[1]);
return 0;
}
1.5 数组作为函数参数的深度剖析
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
void show_value(int arr[], int capacity);
int main(int argc, char const *argv[])
{
int arr[20] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
show_value(arr, 10);
return 0;
}
void show_value(int arr[], int capacity)
{
/*
注意
1. 数组作为函数的参数,提供给函数内部的数据实际上是
数组在内存空间的首地址
2. 在仅具备地址的情况下,无法操作后续的数组元素,因为
无法知晓操作的内存边界,要求必须提供 capacity 数组容
量限制操作范围
3. 数组 capacity 需要进行必要的合法性判断
3.1 必须大于 0
3.2 同时小于
32位 int 最大值
64位 long 最大值
*/
printf("__INT32_MAX__ : %d\n", __INT32_MAX__);
// printf("arr[10] = %d\n", arr[10]);
}
// 【墙裂推荐】
for (int i = 0; i < capacity; i++)
{
arr[i] = 2 * i + 1;
}
// 【依托答辩】
for (int i = 0; i < capacity; i++)
{
*(arr + i) = 2 * i + 1;
}
2. 指针作为函数参数【重点】
#include <stdio.h>
void my_swap1(int n1, int n2);
void my_swap2(int *p1, int *p2);
int main(int argc, char const *argv[])
{
int n1 = 100;
int n2 = 20;
my_swap1(n1, n2);
/*
n1 = 100, n2 = 20; 数据未发生改变
因为当前函数所需参数为 int 类型,在 main 函数中
n1 和 n2 提供给函数的只是变量存储的数据内容,并
没有将 main 函数中的变量提供给函数使用。
【数值传递】
*/
printf("n1 = %d, n2 = %d\n", n1, n2);
/*
void my_swap2(int *p1, int *p2);
当前函数所需参数是两个指向内存空间为 int 类型的指针,
要求用户提供的是满足类型要求的地址,实际参数是&n1 和
&n2。相当于将 n1 和 n2 在内存中的空间首地址提供给函
数使用,函数内部可以根据地址直接访问对应的内存空间操
作数据
【地址传递】
*/
my_swap2(&n1, &n2);
printf("n1 = %d, n2 = %d\n", n1, n2);
return 0;
}
void my_swap1(int n1, int n2)
{
n1 += n2;
n2 = n1 - n2;
n1 -= n2;
}
void my_swap2(int *p1, int *p2)
{
*p1 += *p2;
*p2 = *p1 - *p2;
*p1 -= *p2;
}
- 感谢你赐予我前进的力量
赞赏者名单
因为你们的支持让我意识到写文章的价值🙏
本文是原创文章,采用 CC BY-NC-ND 4.0 协议,完整转载必须注明来自 卡卡罗特
评论
匿名评论
隐私政策
你无需删除空行,直接评论以获取最佳展示效果