https://blog.csdn.net/constantin_/article/details/79575638

就上面的博客作一下笔记:

关于【int (*p)[3]】与【int *p[3]】两个的区别

https://blog.csdn.net/sayesan/article/details/39001609

技巧1:注意*与[与变量结合的优先顺序,p有可能是指针,也有可能是数组,也有可能是函数名。

技巧2:关于“指针类型”的判定:

1)首先,要确保变量就是一个指针类型。

2)去掉变量名,剩下的就是指针类型。

技巧3:关于“指针所指向的类型”的判定:

1)首先,要确保变量就是一个指针类型。

2)去掉变量名指针的声明符*,剩下的就是指针指向的类型。

void如果来修饰指针运算符*,就代表是任意类型的指针。

int (*p)[3];

关于复杂指针类型,上面这个类型。注意(*p)这个括号,仅仅是用来约束运算符优先级的。不要和下面的指针类型混淆。

Int (*p)(int);

上面这个类型。注意(*p)这个括号,代表p指向的是一个函数。

所以在判断(*p)指针的指向的内容类型时,可以将(*p)同时去掉再行判断 。

指针打印:采用%p

1)对于“例二”

如果ptr指针类型声明为char *,ptr++之后的打印结果为b。

#include "stdafx.h"

#include

int _tmain(int argc, _TCHAR* argv[])

{

char a[20]={'a','b','c','d','e','f'};

char *ptr= a; //强制类型转换并不会改变a 的类型

ptr++;

printf("%c",*ptr);

system("pause");

return 0;

}

如果ptr指针类型声明为int *,ptr++之后的打印结果为e。

#include "stdafx.h"

#include

int _tmain(int argc, _TCHAR* argv[])

{

char a[20]={'a','b','c','d','e','f'};

int *ptr=(int *)a; //强制类型转换并不会改变a 的类型

ptr++;

printf("%c",*ptr);

system("pause");

return 0;

}

所以当指针声明成不同的类型,++的效果是不一样的。++和指针的类型有关。

如果指针类型和指针所指向的类型不一致时,要注意++的使用。

2)对于“例三”

#include "stdafx.h"

#include

int _tmain(int argc, _TCHAR* argv[])

{

int array[20]={0};

int *ptr=array;

for(int i=0;i<20;i++)

{

(*ptr)++;

ptr++;

}

for(int i=0;i<20;i++)

{

printf("[%d] = %d\n",i,array[i]);

}

system("pause");

return 0;

}

3)对于“例四”

#include "stdafx.h"

#include

int _tmain(int argc, _TCHAR* argv[])

{

char a[20]="You_are_a_girl";

int *ptr=(int *)a;

ptr+=1;

printf("%d\n",*ptr);

system("pause");

return 0;

}

对行%d,*ptr输出的是1600483937

对行%c,*ptr输出的是a

这是为什么,请高手解答?

4)对于“例五”

#include "stdafx.h"

#include

int _tmain(int argc, _TCHAR* argv[])

{

char a[20]="You_are_a_girl";

char *p=a;

char **ptr=&p;

//printf("p=%d\n",p);

//printf("ptr=%d\n",ptr);

//printf("*ptr=%d\n",*ptr);

printf("**ptr=%c\n",**ptr);

ptr++;

//printf("ptr=%d\n",ptr);

//printf("*ptr=%d\n",*ptr);

printf("**ptr=%c\n",**ptr);

system("pause");

return 0;

}

这个例子有点绕,需要注意,上面我来配个图

image.png

**ptr:分解开就是*(*ptr)

*ptr取指ptr所指向的内容,ptr指向的地址是指针变量p所占用的内存地址,ptr所指向的内容就是指针p变量。

*(*ptr) 就是*p,也就是取p所指向的a的首地址的值,所以第一次打印ptr的值是Y。

ptr++,就是得明白指针的++与普通的运算符是不一样的(指针变量的++,代表它所指向的个体的内存地址的递增,且增长单位为指针类型所占字节个数)。

ptr++,也就是 ptr所指向的地址+4(注意是p的地址+4,并非a的地址+4).

ptr++ ,  就是ptr所指向的内存地址是指针p的内存地址加4个字节的地址,至于这个地址里存储的对象是啥,谁也不知道。

*ptr,ptr新指向内存地址就是下面的这个蓝牙框。 *(*ptr),就是把*ptr当作是一个指针,而*ptr并非一定是一个指针。这样程序可能就会报错。

image.png

5)对于“例9”

假如我像下面这么写,会报一个错误:

#include "stdafx.h"

#include

int _tmain(int argc, _TCHAR* argv[])

{

int array[10]={0,1,2,3,4,5,6,7,8,9},value;

array++;

value=*array;

printf("%d\n",value);

system("pause");

return 0;

}

error C2105: “++”需要左值

上面的错误百度了一个解释:https://blog.csdn.net/hou09tian/article/details/75332576

就是数组名是一个指针,但是不是一个变量。不可能对它进行++运算。++不可使用在常量上

改一下代码:

int _tmain(int argc, _TCHAR* argv[])

{

int array[10]={0,1,2,3,4,5,6,7,8,9},value;

int *ptr = array;

ptr++;

value=*ptr;

printf("%d\n",value);

system("pause");

return 0;

}

结果输出1

其实,说到数组,我还一个 需要补充的:数组元素的内存地址是连续的

通过下面的代码打印:

for(int i = 0; i < 10; i++){

printf("array[%d] address = %d\n",i,&array[i]);

}

image.png

6)对于“例十”

strcpy函数,会将char *指针所指向的字符串复制,而不仅仅是一个字符。

printf("%s",array);    %s是从起始位置输出字符直到遇到\0为止,所以%s输出char[]数组,会输出整个串。

关于strcpy函数的详解:

https://blog.csdn.net/okawari_richi/article/details/57411796

7)对于“例十一”  (数组和指针)

sizeof 函数:https://blog.csdn.net/u012520854/article/details/53511154

http://blog.sina.com.cn/s/blog_4badbe8e0100qb0s.html (详细说明数组名与指针的关系)

8)对于“例十二”  (结构体和指针)

https://www.cnblogs.com/winifred-tang94/p/5843440.html

成员调用的方法(->左边必须是指针,"."左边必须是实体)

特别注意结构体与数组,和指针的关系是不一样的。

image.png

对于*(ptr +1)打印的不是结构体的第2个元素,很奇怪。难道数组名与结构体名不一样?

printf("%s\n","----------结构体名取结构体正常数据------------------");

printf("%d\n",*ss);

printf("%d\n",*(ss+1));

增加上述代码,工程一编译就报错:

错误1error C2100: 非法的间接寻址

错误2error C2676: 二进制“+”: “wmain::MyStruct”不定义该运算符或到预定义运算符可接收的类型的转换

所以我得出一个结论,数组名与结构体名有完全不一样的特性:结构体名不能当成指针使用,结构体名不是指针常量。

注意这行代码:

struct MyStruct *ptr=&ss;

假如ss是数组,上面的代码就不用加&号了。

struct MyStruct *ptr=ss;

但是结构体会报错:

错误1error C2440: “初始化”: 无法从“wmain::MyStruct”转换为“wmain::MyStruct *”

这就更加证明了结构体名不是指针常量这个结论 。

继续修改代码:

image.png

注意上面的打印结果,通过pstr取的结构体元素地址是正确的,但是ptr取的结构体元素地址是错误的。

注意代码中ptr与pstr的定义:

struct MyStruct *ptr=&ss;

int *pstr=(int*)&ss;

ptr指向的类型是 MyStruct,指向的对象为结构体实体ss。

pstr指向的类型是int,指向的对象为结构体的实体ss的首元素。

ptr+1,就是&ss这个地址+sizeof(MyStruct),就是&ss+16。

pstr+1,就是&ss这个地址+sizeof(int),就是&ss+4。

--------------------------------------------------------------------------------------------

|   结构体与数组的共性:

|        1)结构体实体的地址和结构体第一个元素的地址一样, 各元素的地址也是连续的。(特殊情况也有不连续的)

|             数组实体的地址和数组第一个元素的地址一样, 各元素的地址也是连续的。

|        2)数组和结构体自身的实体(变量)并不占据独立的内存(和首元素地址一样),只有元素才占用真正的内存地址,

|             它只是标明自身的元素是一组特殊的数据结构, 通过实体封装,便于元素的访问。

|

|  结构体与数组的区别:

|       1)数组名是指针常量,但是结构体名和指针没有任何的关系。

--------------------------------------------------------------------------------------------

9)对于“例十三”

注意作者对结构体的特殊之处的解释

10)指针类型的转换

可以把指针的值当作一个整数取出来,也可以把一个整数值当作地址赋给一个指针

11) 指针安全问题

这个很重要

使用指针必须要清楚指针指向了哪里

©著作权归作者所有:来自51CTO博客作者屠夫章哥的原创作品,如需转载,请注明出处,否则将追究法律责任

c语言指针慕课,C语言指针相关推荐

  1. c语言指针慕课,C语言-指针

    指针pointer 数据类型决定了变量可以表示的数值范围.除此之外,表示变量在内存中生命期范围存储期以及变量名也都是变量的重要属性. 取址运算符-address operator单目运算符`& ...

  2. 关于C语言中的数组指针、指针数组以及二级指针

    概念解释 数组指针:首先它是一个指针,它指向一个数组,即指向数组的指针:在32 位系统下永远是占4 个字节,至于它指向的数组占多少字节,不知道.数组指针指向的是数组中的一个具体元素,而不是整个数组,所 ...

  3. C语言指针数组与数组指针的区别

    C语言指针数组与数组指针的区别 首先,顾名思义 数组指针是一个指针,是指向一个数组的指针,如 int (a*)[5]:这就是一个指向含有5个元素的数组的指针 指针数组是一个数组,它包含的元素全是指针变 ...

  4. 为什么指针被誉为 C 语言灵魂?

    作者 | 编程指北 来源 |  编程指北(ID:cs_dev) 这一篇的文章主题是「指针与内存模型」. 说到指针,就不可能脱离开内存,学会指针的人分为两种,一种是不了解内存模型,另外一种则是了解. 不 ...

  5. C语言指针高级部分:void指针和数据指针

    概念 void指针     数据指针 void指针 void指针的基本概念 void的意思就是"无类型",void指针则为"无类型指针",void指针可以指向任 ...

  6. 【C 语言】二级指针作为输入 ( 自定义二级指针内存 | 二级指针排序 | 通过 交换指针指向的内存数据 方式进行排序 )

    文章目录 一.二维指针 排序 ( 通过 交换指针指向的内存数据 方式进行排序 ) 二.完整代码示例 一.二维指针 排序 ( 通过 交换指针指向的内存数据 方式进行排序 ) 在上一篇博客 [C 语言]二 ...

  7. 【C 语言】二级指针作为输入 ( 自定义二级指针内存 | 二级指针 排序 | 通过 交换指针方式 进行排序 )

    文章目录 一.二维指针 排序 ( 通过 交换指针方式 进行排序 ) 二.完整代码示例 一.二维指针 排序 ( 通过 交换指针方式 进行排序 ) 在上一篇博客 [C 语言]二级指针作为输入 ( 二维指针 ...

  8. 【C++ 语言】引用 ( 引用简介 | 指针常量 | 常量指针 | 常引用 | 引用参数 | 引用 指针 对比 )

    文章目录 I . 引用概念 II . 引用声明 III . 引用 地址 内存 分析 IV . 常引用 V . 引用作为参数 VI . 引用 与 指针 对比 I . 引用概念 C++ 对 C 扩充 : ...

  9. 【C 语言】指针 与 数组 ( 指针 | 数组 | 指针运算 | 数组访问方式 | 字符串 | 指针数组 | 数组指针 | 多维数组 | 多维指针 | 数组参数 | 函数指针 | 复杂指针解读)

    相关文章链接 : 1.[嵌入式开发]C语言 指针数组 多维数组 2.[嵌入式开发]C语言 命令行参数 函数指针 gdb调试 3.[嵌入式开发]C语言 结构体相关 的 函数 指针 数组 4.[嵌入式开发 ...

最新文章

  1. 真惨!连各大编程语言都摆起地摊了!
  2. 学会python爬虫怎么赚钱-学会python爬虫怎么赚钱
  3. 智能的定义是什么?如何正确理解智能家居?
  4. anki vector robot入门语音指令大全
  5. Java8 Lambda总结
  6. python中什么是按位取反_Python学习中的“按位取反”笔记总结
  7. @程序员,京东面试官让你谈谈注册中心的问题!
  8. 函数adapthisteq
  9. java 数组溢出异常,Java数组超出范围时如何处理多个异常?
  10. Exploring Architectural Ingredients of Adversarially Robust Deep Neural Networks
  11. 大数据时代下的企业管理创新
  12. python相关专业-使用 Python 查找分类变量和连续变量之间的相关性
  13. 用大数据把电视观众“挖”出来
  14. 华为 eNSP 打开警告:请将eNSP相关应用程序添加到windows firewall的允许程序列表,并允许其在公用网络上运行!
  15. 苹果A13芯片细节曝光,大幅提升AI性能
  16. 提分必练,中创教育PMP全真模拟题分享来喽
  17. CSDN 自定义博客栏目
  18. 用Windows内置工具测试硬盘速度
  19. 我,40岁码农,还在荷兰写低级代码,不敢回国…
  20. URL格式java_URLConnection格式与用法

热门文章

  1. 万万没想到!ModelArts与AppCube组CP了
  2. 【Python成长之路】python并发学习:多进程与多线程的用法及场景介绍
  3. 【华为云技术分享】【我的物联网成长记16】玩转设备固件升级
  4. 带着canvas去流浪系列之八 碰撞
  5. 【nodejs原理源码赏析(2)】KOA中间件的基本运作原理
  6. SpringBoot和Elasticsearch集成
  7. MacOS12+SublimeText+Skim无法正常跳转Skim的问题与解决
  8. PyQt5学习笔记(二) 文本控件及使用
  9. 小数加分数怎样计算讲解_反渗透阻垢剂的加药量怎样计算?
  10. python中级_python复习之中级