文章目录
- 一、指针步长
- 二、复杂指针阅读技巧
一、指针步长
指针 也是一种 数据类型 , 其 类型 是 指针 指向的 内存空间 的 数据类型 ;
指针步长 : 根据 指针 指向的 内存空间 数据类型 确定 ;
代码语言:javascript复制int *p;
p ;
指针作为 函数参数 时 , 如果 函数形参 有多级指针 , 并且带 数组 / 函数 等相关复杂元素 ,
- 编译 : 从编译器角度出发 , 只要是 指针类型 的参数 , 就在 栈内存 中 , 为其 分配 4 字节数据 ;
- 使用 : 当在 函数 中 , 使用该指针指向的数据时 , 才关心该指针指向的数据结构 ;
二、复杂指针阅读技巧
如果遇到复杂指针类型 , 参考 【C 语言】指针 与 数组 ( 指针 | 数组 | 指针运算 | 数组访问方式 | 字符串 | 指针数组 | 数组指针 | 多维数组 | 多维指针 | 数组参数 | 函数指针 | 复杂指针解读)3. 解读 复杂的 指针声明 ( 难点 重点 | ①找出中心标识符 ②先右 后左 看 确定类型 提取 ③ 继续分析 左右看 … ) 博客章节进行分析 ;
指针 定义 复杂性来源 :
- 1.数组指针 : 数组指针类型为 int (*) [5] , 即 一个指向 int[5] 的指针, 其指针变量名称写在中间的括号中
- 2.函数指针 : 函数指针类型为 int(*)(int, int), 即 一个指向 int(int, int) 类型函数的指针, 其指针变量名称写在中间的括号中 ;
- 3.数组指针混合函数指针 : 如果出现了 数组指针 指向一个函数, 这个指针可读性很差, 理解需要一定的功力 ;
复杂指针阅读技巧 ( 主要是 区分 函数指针 和 数组指针 ) 右左法则 :
- 1.最里层标示符 : 先找到最里层的圆括号中的标示符; 数组指针和函数指针的标示符 ( 指针变量名 ) 都在中间的圆括号中, 因此该步骤先找到指针变量名
- 2.右左看 : 先往右看, 再往左看 ;
- 3.确定类型 : 遇到 圆括号 “()” 或者 方括号 “[]” 确定部分类型, 调转方向 ; 遇到 * 说明是指针 , 每次确定完一个类型 , 将该类型提取出来 , 分析剩下的 ; 一种可能性 : int (*) [5] , 遇到中括号说明是数组指针类型, int(*)(int, int) , 遇到圆括号 说明是函数指针类型 ;
- 4.重复 2 , 3 步骤 : 一直重复, 直到 指针 阅读结束 ;
指针阅读案例 :
- 1.解读案例 1 :
/*
解读步骤 :
1. 研究第一个标示符 p
( 1 ) 先找最里层的圆括号中的 标示符 p
( 2 ) p 往右看, 是圆括号, 然后往左看, 是 * , 可以确定 p 是一个指针
( 3 ) 将 (*p) 拿出来, 然后看剩下的部分, 右看是 圆括号 (, 明显是个函数类型, int (int*, int (*f)(int*)) 很明显是一个 函数类型
2. 解读函数类型 int (int*, int (*f)(int*))
( 1 ) 函数类型 int (int*, int (*f)(int*)) 的返回值类型是 int 类型
( 2 ) 函数类型的第一个参数类型是 int* , 即 int 类型指针类型
( 3 ) 函数类型的 第二个参数是 int (*f)(int*) 也是一个函数类型指针
3. 解读 int (*f)(int*) 参数
( 1 ) 标示符是 f, 由看 是 圆括号, 坐看是 * , 因此 f 是一个指针;
( 2 ) 将(*f) 提取出来, int(int*) 是一个函数类型, 其返回值是 int 类型, 参数是 int* 指针类型
总结 :
指针 p 是一个指向 int(int*, int (*f)(int*)) 类型函数的指针,
函数返回值是 int 类型, 参数是 int* 指针类型 和 int (*)(int*) 函数指针 类型
指针 f 是一个指向 int(int*) 类型函数的指针, 其返回值是 int 类型, 参数是 int* 指针类型
*/
int (*p) (int*, int (*f)(int*));