指针笔试题讲解(让指针变得简单易懂)

数组名的理解 :   数组名就是首元素地址 

 但是有两个例外:

  1. sizeof(数组名)这里的数组名表示整个数组的大小,sizeof(数组名)计算的是整个数组的大小,单位是字节 

 2. &数组名   这里的数组名表示整个数组 ,&数组名取出的是数组的地址

目录

一.笔试题 ( 1 )

sizeof的解释

二.笔试题 ( 2 )

strlen函数的解释 

三 .笔试题 ( 3 )

四. 笔试题 ( 4 )

五.笔试题 ( 5 ) 

一.笔试题 ( 1 )

博主个人建议 : 自己先做一遍,看看哪个做错了,然后再看博主的解释

                          做对的题,自己想想因为什么得这个数,看看与博主的解释一样不

sizeof的解释

sizeof ()是C语言中常用的运算符,可以计算操作数的大小。. sizeof的结果是无符号整数类型,通常用size_t表示。. sizeof可以应用于各种数据类型,包括基本的数据类型,例如整数和浮点类型,指针类型和符合数据类型,结构体等等。

int main()
{//一维数组int a[] = { 1,2,3,4 };printf("%d\n", sizeof(a)); printf("%d\n", sizeof(a + 0));printf("%d\n", sizeof(*a));printf("%d\n", sizeof(a + 1));printf("%d\n", sizeof(a[1]));printf("%d\n", sizeof(&a));printf("%d\n", sizeof(*&a));printf("%d\n", sizeof(&a + 1));printf("%d\n", sizeof(&a[0]));printf("%d\n", sizeof(&a[0] + 1));	return 0;
}

博主自己做了一遍    printf("%d\n", sizeof(&a));   我认为这个打印的是16                                        因为 ,&数组名  ,这里的数组名表示整个数组 ,但是事实上我只想对了一半 

&a - 是取出数组的地址,但是数组的地址也是地址,是地址就是4/8个Byte (在32位下是4个字节,64位下是8个字节)  数组的地址 和 数组首元素的地址 的本质区别是类型的区别,并非大小的区别

上面的代码解释如下:

int main()
{//一维数组int a[] = { 1,2,3,4 };//4个元素,每个元素使int类型(4个字节)printf("%d\n", sizeof(a));//数组名a单独放在sizeof内部,数组名表示整个数组,计算的是整个数组的大小单位是字节,是16字节printf("%d\n", sizeof(a + 0));//a并非单独放在sizeof内部,也没有&,所以数组名a是数组首元素的地址,a+0还是首元素的地址//是地址大小就是4/8 Byteprintf("%d\n", sizeof(&a));// &a - 是取出数组的地址,但是数组的地址也是地址,是地址就是4/8个Byte//数组的地址 和 数组首元素的地址 的本质区别是类型的区别,并非大小的区别printf("%d\n", sizeof(*&a));//对数组指针解引用访问一个数组的大小,单位是字节//sizeof(*&a) --- sizeof(a) printf("%d\n", sizeof(&a + 1));//&a数组的地址,&a+1还是地址,是地址就是4/8个字节printf("%d\n", sizeof(&a[0]));//&a[0]是首元素的地址, 计算的是地址的大小 4/8 个字节printf("%d\n", sizeof(&a[0] + 1));//&a[0]是首元素的地址,&a[0]+1就是第二个元素的地址,大小4/8个字节return 0;
}

拓展:&a[0] + 1是第二个元素的地址,大小 4/8 个字节

同样表示第二个元素地址的写法还有 &a[1]   &a[0]+1   a+1


二.笔试题 ( 2 )

指针变量的大小和类型无关,不管什么类型的指针变量,大小都是4/8个字节
指针变量是用来存放地址的,地址存放需要多大空间,指针变量的大小就是几个字节
32位环境下,地址是32个二进制位,需要4个字节,所以指针变量的大小就是4个字节
64位环境下,地址是64个二进制位,需要8个字节,所以指针变量的大小就是8个字节 

strlen函数的解释 

strlen函数,只有遇到 ' \0 ' 时才停止  

#include <string.h>int main()
{//字符数组char arr[] = { 'a','b','c','d','e','f' };printf("%d\n", strlen(arr));printf("%d\n", strlen(arr + 0));printf("%d\n", strlen(*arr));printf("%d\n", strlen(arr[1]));printf("%d\n", strlen(&arr));printf("%d\n", strlen(&arr + 1));printf("%d\n", strlen(&arr[0] + 1));printf("%d\n", sizeof(arr));printf("%d\n", sizeof(arr + 0));printf("%d\n", sizeof(*arr));printf("%d\n", sizeof(arr[1]));printf("%d\n", sizeof(&arr));printf("%d\n", sizeof(&arr + 1));printf("%d\n", sizeof(&arr[0] + 1));return 0;
}

自己要先做一遍!!!!!!!!!!!!!!!!再看解释

博主,自己做的时候,printf("%d\n", sizeof(*arr)); 

我认为它应该是4个字节,又是想对了一半

arr是首元素的地址,正常来说地址是4/8个字节,但是它是*arr

*arr就是第一个元素所以它是 1 个字节
    

int main()
{//字符数组char arr[] = { 'a','b','c','d','e','f' };//6printf("%d\n", strlen(arr));//随机值,arr是首元素的地址	printf("%d\n", strlen(arr + 0));//随机值,arr是首元素的地址, arr+0还是首元素的地址printf("%d\n", strlen(*arr));//err,arr是首元素的地址, *arr就是首元素 - 'a' - 97//站在strlen的角度,认为传参进去的'a'-97就是地址,97作为地址,直接进行访问,就是非法访问printf("%d\n", strlen(arr[1]));//err, 'b' - 98printf("%d\n", strlen(&arr));//随机值//&arr -- char (*)[6]//const char*printf("%d\n", strlen(&arr + 1));//随机值printf("%d\n", strlen(&arr[0] + 1));//随机值printf("%d\n", sizeof(arr));//6 数组名arr单独放在sizeof内部,计算的是整个数组的大小,单位是字节printf("%d\n", sizeof(arr + 0));//arr是首元素的地址==&arr[0],是地址就是4/8个字节printf("%d\n", sizeof(*arr));//arr是首元素的地址,*arr就是首元素,大小就是1Byteprintf("%d\n", sizeof(arr[1]));//1printf("%d\n", sizeof(&arr));//&arr是数组的地址,sizeof(&arr)就是4/8个字节printf("%d\n", sizeof(&arr + 1));//&arr+1 是跳过数组后的地址,是地址就是4/8个字节printf("%d\n", sizeof(&arr[0] + 1));//第二个元素的地址,是地址就是4/8Bytereturn 0;
}

    


三 .笔试题 ( 3 )

int main()
{char arr[] = "abcdef";printf("%d\n", strlen(arr));printf("%d\n", strlen(arr + 0));printf("%d\n", strlen(*arr));printf("%d\n", strlen(arr[1]));printf("%d\n", strlen(&arr));printf("%d\n", strlen(&arr + 1));printf("%d\n", strlen(&arr[0] + 1));*/printf("%d\n", sizeof(arr));printf("%d\n", sizeof(arr + 0));printf("%d\n", sizeof(*arr));printf("%d\n", sizeof(arr[1]));printf("%d\n", sizeof(&arr));printf("%d\n", sizeof(&arr + 1));printf("%d\n", sizeof(&arr[0] + 1));return 0;
}

 自己要先做一遍!!!!!!!!!!!!!!!!再看解释 ( 重要的事情说三遍)

 printf("%d\n", sizeof(arr));我认为这个是 6 但是结果是7,因为我少算了一个 ' \0 '

a b c d e f \0   共7个

(每个笔试题必须要错一个,脑袋疼)
 

int main()
{char arr[] = "abcdef";printf("%d\n", strlen(arr));//字符串长度,遇到'\0'停止所以是6printf("%d\n", strlen(arr + 0));//字符串长度,遇到'\0'停止,6printf("%d\n", strlen(*arr));//err 传参错误,应该传的是字符串的地址printf("%d\n", strlen(arr[1]));//传参错误,道理同上printf("%d\n", strlen(&arr));//数组首元素地址,6printf("%d\n", strlen(&arr + 1));//随机值printf("%d\n", strlen(&arr[0] + 1));//从b开始往后所以答案是5printf("%d\n", sizeof(arr));//整个数组包括'\0'所以是7printf("%d\n", sizeof(arr + 0));//第一个元素地址printf("%d\n", sizeof(*arr));//第一个元素地址printf("%d\n", sizeof(arr[1]));//第二个元素地址printf("%d\n", sizeof(&arr));//整个数组地址printf("%d\n", sizeof(&arr + 1));//跳过整个数组后的地址printf("%d\n", sizeof(&arr[0] + 1));//第二个元素地址return 0;
}

四. 笔试题 ( 4 )

int main()
{char* p = "abcdef";printf("%d\n", strlen(p));printf("%d\n", strlen(p + 1));printf("%d\n", strlen(*p));printf("%d\n", strlen(p[0]));printf("%d\n", strlen(&p));printf("%d\n", strlen(&p + 1));printf("%d\n", strlen(&p[0] + 1));printf("%d\n", sizeof(p));printf("%d\n", sizeof(p + 1));printf("%d\n", sizeof(*p));printf("%d\n", sizeof(p[0]));printf("%d\n", sizeof(&p));printf("%d\n", sizeof(&p + 1));printf("%d\n", sizeof(&p[0] + 1));return 0;}

我这次错了很多 (可能是眼睛太大了,没看见是 char* p )

 大家在看东西的时候一定要观察仔细!!!!

       printf("%d\n", strlen(p + 1));首元素地址+1,从b开始所以应该是5

       printf("%d\n", strlen(&p)    随机值,

       printf("%d\n", strlen(&p + 1));随机值
大家有什么不懂的可以去看笔试题 ( 3 )的解释

	printf("%d\n", strlen(p));   //6printf("%d\n", strlen(p + 1));  //5printf("%d\n", strlen(*p));   //errprintf("%d\n", strlen(p[0])); //errprintf("%d\n", strlen(&p));   //随机值printf("%d\n", strlen(&p + 1));//随机值printf("%d\n", strlen(&p[0] + 1));    //5printf("%d\n", sizeof(p));//4/8 计算的是指针变量的大小printf("%d\n", sizeof(p + 1));//p+1还是地址,大小是4/8个字节printf("%d\n", sizeof(*p));//1个字节, *p == 'a'printf("%d\n", sizeof(p[0]));//1个字节, p[0]--> *(p+0) --> *p == 'a';printf("%d\n", sizeof(&p));//4/8个字节,&p 是地址printf("%d\n", sizeof(&p + 1));//&p是地址,&p+1还是地址,是地址就是4/8个字节printf("%d\n", sizeof(&p[0] + 1));

五.笔试题 ( 5 )

int a[3][4] = { 0 };printf("%d\n", sizeof(a));printf("%d\n", sizeof(a[0][0]));printf("%d\n", sizeof(a[0]));printf("%d\n", sizeof(a[0] + 1));printf("%d\n", sizeof(*(a[0] + 1)));printf("%d\n", sizeof(a + 1));printf("%d\n", sizeof(*(a + 1)));printf("%d\n", sizeof(&a[0] + 1));printf("%d\n", sizeof(*(&a[0] + 1)));printf("%d\n", sizeof(*a));printf("%d\n", sizeof(a[3]));

int main()
{int a[3][4] = { 0 };printf("%zd\n", sizeof(a));//48-数组名a单独放在了sizeof内存,表示整个数组,sizeof(a)计算的是数组的大小,单位是字节printf("%zd\n", sizeof(a[0][0]));//4-a[0][0]是数组的第一行第一个元素,这里计算的就是一个元素的大小,单位是字节printf("%zd\n", sizeof(a[0]));//16 - a[0]是第一行这个一维数组的数组名,数组名单独放在了sizeof内部//a[0]就表示整个第一行这个一维数组,sizeof(a[0])计算的整个第一行这个一维数组的大小printf("%zd\n", sizeof(a[0] + 1));//4/8 - a[0]并非单独放在sizeof内部,也没有&,所以a[0]表示第一行这个一维数组首元素的地址//也就是第一行第一个元素的地址//a[0] <---> &a[0][0]//a[0]+1 ---> &a[0][1]printf("%zd\n", sizeof(*(a[0] + 1)));//4 - a[0] + 1是第一行第二个元素的地址,*(a[0] + 1))就是第一行第二个元素//printf("%zd\n", sizeof(a + 1));//4/8//a 作为二维数组的数组名,并没有单独放在sizeof内部,也没有&,a就是数组首元素的地址,也就是第一行的地址, a 的类型是 int(*)[4]//a+1 就是第二行的地址,类型是:int(*)[4]//printf("%zd\n", sizeof(*(a + 1)));//16 a+1是第二行的地址,*(a+1)就是第二行,计算的就是第二行的大小//另外一个角度理解:*(a+1) -- a[1]//sizeof(a[1]) - a[1]这个第二行的数组名,单独放在了sizeof内部,计算的是第二行的大小printf("%zd\n", sizeof(&a[0] + 1));//4/8//a[0]是第一行的数组名,&a[0]取出的是数组的地址,取出的是第一行这个一维数组的地址,类型就是int(*)[4]//&a[0]+1 就是第二行的地址,类型就是int(*)[4]printf("%zd\n", sizeof(*(&a[0] + 1)));//*(&a[0] + 1)得到的就是第二行,计算的就是第二行的大小printf("%zd\n", sizeof(*a));//16//a表示数组首元素的地址,也就是第一行的地址//*a 就是第一行,也就相当于是第一行的数组名//*a--> *(a+0) -- a[0]//printf("%zd\n", sizeof(a[3]));//16-不会越界,//a[3] --    arr[0]//int [4]    int [4]//int a = 10;//sizeof(a);//sizeof(int)//表达式 有2个属性:值属性,类型属性//2+3    = 5//       = intreturn 0;
}

新人博主,如果有地方解释的不对或者不清晰,麻烦大佬们海涵,如果可以麻烦从评论区指出,我一定会加以修改,万分感谢

最后麻烦大佬们动一下发财的小手一键三连,千万分感谢

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/136631.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

9月19日作业

完成文本编辑器的保存工作-代码&#xff1a; void Widget::on_pushButton_4_clicked() {//创建保存文件对话框QString filename QFileDialog::getSaveFileName(this,"保存文件","./","All(*.*);;Text files (*.txt)");//创建一个文件对象&…

福建厦门航空飞机发动机零部件检测3D测量尺寸偏差比对-CASAIM中科广电

航空航天是一个创新型发展国家的尖端命脉&#xff0c;代表着一个国家科学技术的先进水平。在航空航天工业的发展和组成领域中&#xff0c;对于在制造业中的航空航天产品零部件精度要求十分严苛&#xff0c;从前期的设计、中期建造、后期维修检测&#xff0c;任何一个环节、任何…

java CAS详解(深入源码剖析)

CAS是什么 CAS是compare and swap的缩写&#xff0c;即我们所说的比较交换。该操作的作用就是保证数据一致性、操作原子性。 cas是一种基于锁的操作&#xff0c;而且是乐观锁。在java中锁分为乐观锁和悲观锁。悲观锁是将资源锁住&#xff0c;等之前获得锁的线程释放锁之后&am…

Nginx配置负载均衡时访问地址无法生效

场景还原 今天有小伙伴练习Nginx配置负载均衡时总是无法使用配置好的网址访问 配置文件信详情 http {# 负载均衡 后端IP地址和端口 webservers 策略 轮询upstream webservers{server 192.168.1.100:8080 weight90; server 127.0.0.1:8080 weight10; }server{listen 80;ser…

C#使用OpenCv(OpenCVSharp)图像轮廓多边形逼近和轮廓最小矩形实例

本文实例演示C#语言中如何使用OpenCv(OpenCVSharp)对图像轮廓多边形逼近和轮廓最小矩形实例。 多边形逼近的目的是减少轮廓的点数,但看起来轮廓形状差不多。 最小矩形:面积更小的矩形,把轮廓包围起来实例 创建winform项目,添加控件和事件 添加类 using System; using…

学习路之PHP--laravel postman 提交表单出现419错误

问题图片 解决&#xff1a; 白名单 有时候你可能希望设置一组不需要 CSRF 保护的 URL 。例如&#xff0c;如果你正在使用 Stripe 处理付款并使用了他们的 webhook 系统&#xff0c;你会需要从 CSRF 的保护中排除 Stripe webhook 处理程序路由&#xff0c;因为 Stripe 不知道要发…

VSCode『SSH』连接服务器『GUI界面』传输

前言 最近需要使用实验室的服务器训练带有 GUI 画面的 AI 算法模型&#xff08;pygame&#xff09;&#xff0c;但是我是使用 SSH 连接的&#xff0c;不能很好的显示模型训练的效果画面&#xff0c;所以下面将会讲解如何实现 SSH 连接传输 Linux GUI 画面的 注&#xff1a;我们…

vs2022 创建一个同时支持.net480和.net6.0的WPF项目

新建WPF项目&#xff0c;不要选.NET Framework框架的。如下图所示&#xff0c;选择第一个。&#xff08;选择.NET Framework框架改成.net6.0会报错&#xff09; 用记事本打开项目的csproj文件&#xff0c;修改TargetFrameworks标签&#xff0c;如下所示&#xff1a; <Pro…

解决flutter不识别yaml里面配置的git项目

解决办法找到相应的 git路径&#xff0c;然后手动 git pull 暂时先用这个笨方法&#xff0c;后面有更好的解决办法了再说 studio 自己拉取的项目里面没有ios 和lib包

STM32-无人机-电机-定时器基础知识与PWM输出原理

电机控制基础——定时器基础知识与PWM输出原理 - 掘金单片机开发中&#xff0c;电机的控制与定时器有着密不可分的关系&#xff0c;无论是直流电机&#xff0c;步进电机还是舵机&#xff0c;都会用到定时器&#xff0c;比如最常用的有刷直流电机&#xff0c;会使用定时器产生PW…

5.2 磁盘CRC32完整性检测

CRC校验技术是用于检测数据传输或存储过程中是否出现了错误的一种方法&#xff0c;校验算法可以通过计算应用与数据的循环冗余校验&#xff08;CRC&#xff09;检验值来检测任何数据损坏。通过运用本校验技术我们可以实现对特定内存区域以及磁盘文件进行完整性检测&#xff0c;…

纯js实现html指定页面导出word

因为最近做了范文网站需要&#xff0c;所以要下载为word文档&#xff0c;如果php进行处理&#xff0c;很吃后台服务器&#xff0c;所以想用前端进行实现。查询github发现&#xff0c;确实有这方面的插件。 js导出word文档所需要的两个插件&#xff1a; FileSaver.js jquery.w…

使用香橙派学习 Linux的守护进程

Q&#xff1a;什么是守护进程 A&#xff1a;Linux Daemon&#xff08;守护进程&#xff09;是运行在后台的一种特殊进程。它独立于控制终端并且周期性地执行 某种任务或等待处理某些发生的事件。它不需要用户输入就能运行而且提供某种服务&#xff0c;不是对整个系统就是对某个…

简述TCP三次握手,四次挥手

前言&#xff1a; 通常大多数认为三次握手、四次挥手是HTTP协议产生的。这是一个错误的认知&#xff0c;实际上HTTP协议并不参与握手以及挥手过程&#xff0c;三次握手四次挥手均是在TCP协议层上进行的&#xff0c;而HTTP协议只是在已建立 TCP连接的基础上&#xff0c;进行通信…

讯飞实时语音读写,并播放录音,上传录音文件

需求描述&#xff1a;使用讯飞实现录音实时识别&#xff0c;并且可以播放以及上传。 首先想到使用到这个组件voice-input-button2&#xff0c;他集成了讯飞语音读写的功能 &#xff0c;插件地址&#xff1a;https://github.com/ferrinweb/voice-input-button2根据文档集成成功…

TypeScrip

TypeScript强调了两个重要的特性--类型系统、适用于任何规模的项目 1、TypeScript 从名字就可以看出来&#xff0c;类型是其核心的特性。 我们知道&#xff0c;JavaScript是一门非常灵活的编程语言,他有以下一些特点: 没有类型约束&#xff0c;一个变量可以初始化是字符串&a…

c语言进阶部分详解(指针进阶1)

大家好&#xff01;指针的初阶内容我已经写好&#xff0c;可移步至我的文章&#xff1a;c语言进阶部分详解&#xff08;指针初阶&#xff09;_总之就是非常唔姆的博客-CSDN博客 基本内容我便不再赘述&#xff0c;直接带大家进入进阶内容&#xff1a; 目录 一.字符指针 1.讲解…

华为云云服务器云耀L实例评测 | 从零到一:华为云云耀云服务器L实例上手体验

&#x1f337;&#x1f341; 博主猫头虎&#xff08;&#x1f405;&#x1f43e;&#xff09;带您 Go to New World✨&#x1f341; &#x1f984; 博客首页——&#x1f405;&#x1f43e;猫头虎的博客&#x1f390; &#x1f433; 《面试题大全专栏》 &#x1f995; 文章图文…

Android StateFlow初探

Android StateFlow初探 前言&#xff1a; 最近在学习StateFlow&#xff0c;感觉很好用&#xff0c;也很神奇&#xff0c;于是记录了一下. 1.简介&#xff1a; StateFlow 是一个状态容器式可观察数据流&#xff0c;可以向其收集器发出当前状态更新和新状态更新。还可通过其 …

go学习之函数知识

函数 文章目录 函数1.函数入门(1)为什么需要函数&#xff1f;(2)什么是函数&#xff1a;2.包3.函数的调用机制通俗理解调用过程&#xff1a;return语句递归调用 4.函数注意事项和细节讨论5.init函数6.匿名函数7.闭包8.defer9.函数参数的传递方式10.字符串中常用的函数11.时间和…