深入学习指针5,与数组和指针相关的笔试题1(C语言)

前言

Hello,亲爱的小伙伴们,我又来了,,今天呢我们一起来学习一下C语言关于数组和指针的部分经典题目。如果觉得不错的话不要忘了点赞,收藏、关注,你的支持就是我更新的最大动力!!

好,废话不多说,开始我们今天的正题!! 

1.sizeof和strlen的对比

1.1 sizeof 

在学习操作符的时候,我们学习了sizeof,sizeof是计算变量所占内存空间大小的,单位是字节,如果操作数是类型的话,计算的是所用类型创建变量的占用空间的大小。

sizeof只关注内存空间的大小,不在乎内存中存了什么。

 比如:

 #inculde <stdio.h>int main(){int a = 10;printf("%d\n", sizeof(a));printf("%d\n", sizeof a);printf("%d\n", sizeof(int));return 0;}

1.2 strlen 

strlen是C语言的库函数,功能是求字符串的长度。原型是:

 size_t strlen ( const char * str );

统计的是聪strlen函数的参数str中的这个地址向后,\0之前的字符串中的字符个数。

strlen会一直计数,知道找到  \0   ,可以越界查找!!

也就是说,strlen函数会关注str所指向的字符串的内容!! 

由此,我们比较可得:

2.数组和指针笔试题的讲解 

然后有了上面的知识基础,我们就能来看看这些题了

2.1 一维数组

 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));

我们可以更具之前学过的知识来判断,这些语句的运行结果分别是是什么呢?

1.我们可知,a为一个一维数组,直接的a在大多数的情况 表示首元素的地址,但有例外,就像第一条语句一样,在操作符sizeof中,a就指代整个数组,计算的是整个数组的大小,单位为字节,所以:

 第一条语句的运行结果为:16

2.第二个语句显然不是单独的数组名出现在sizeof中,所以a+0指代的是数组首元素的地址

地址的所占内存空间大小因平台而异,在VS2022中大致就两种情况 :

     4 or 8

    运行结果为:4 / 8

3.第三条语句 *a指代的就是整个数组的首元素,所以:

结果为 :4

4.  printf("%d\n",sizeof(a+1));

这里a + 1指代的就是第二个元素的地址,故情况与第二条一致!!

     4 or 8


5.  printf("%d\n",sizeof(a[1]));

a[1] ---->*(a + 1),即为一维数组的第二个元素

     4


 6.printf("%d\n",sizeof(&a));

由于&a为整个数组的地址,所以:

4 / 8


7. printf("%d\n",sizeof(*&a));

在这里 解引用+取地址可以相互抵消,就相当于计算整个数组内存占用的大小:
    16
 

8. printf("%d\n",sizeof(&a+1));
 printf("%d\n",sizeof(&a[0]));
 printf("%d\n",sizeof(&a[0]+1));

这三条本质上都是计算的地址的所占空间大小:

   4 / 8

好有了上面的基础,大家能不能试着计算,下面语句的运算结果呢?

 char arr[] = {'a','b','c','d','e','f'};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));

好,这些题大家都做对了几道呢 ,这些语句的分析方法与上面的题相似,这里就不再赘述,有问题的小伙伴可以在品论区友好交流哟。

接下来我们再看下面的代码:

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));

大家先好好看看,能不能找到答案。

上面我有提到,strlen函数在访问计数字符串时,只有遇到 ‘\0'时,才会停止,否则会出现越界访问的问题 

现在我们可以先来看看运行后的结果:

 

咦,为什么会这样呢?

在上面的字符数组中没有存放,‘\0' 

哦,我们现在知道了,在发生越界访问时,要遇到了’/0‘,strlen函数就会停止计数,那什么时候strlen函数会停下来呢,这个我们就不知道了,看因为在内存中,可能会有存储在某些位置的'\0'

使strlen函数停下来,故此时返回的随机值!!

那为什么到第三条语句的时候就出现了问题,无法运行出结果呢?

这个我们就可以从strlen函数的功能结构入手了:

 

看到这里我们可以了解到,strlen函数是通过访问地址来往后读取·字符串的,而第三条语句使将数组的首元素给了strlen函数,函数会将传给他的内容当作地址去访问, 而 a 这个字符作为地址是无效的,于是就不能得到结果!!  第三条与第四条语句都是一样的原理!!

那后面的三条语句又是怎么回事呢?

 

上面我们也知道了,&arr在这里就指代整个数组的地址,得到这个地址后strlen函数会逐字节访问,故效果和传给strlen函数arr数组的首地址相同。

倒数第二条语句 &arr + 1,则就相当&arr跳过了整个arr数组的大小个字节,因为arr有6个元素,故可以得到答案。 

最后一条语句就十分简单了,传给strlen函数的是数组第二个元素的地址,故得到的结果会少一个。

好,接下来大家可以看看下面的代码:

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))

怎么样大加能够看出答案吗,其实这些语句与上面的代码分析逻辑基本相符,但是“” 包住的字符串在末尾会自动为字符串添加上 ' \0'因此就不会再出现上面的越界问题。

那大家就自己练习一下吧。

那我就先去喝口茶~~

大家做出来了吗?作者菌就先将大安放到这了,有问题的话,欢迎uu们到评论区友好讨论哟!!

 

好,今天的学习就先到这里,感兴趣的小伙伴不要忘了点一个三连啊,你的支持就是我更新的动力,咱们下期再见。拜拜!! 

 

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

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

相关文章

机器学习中的聚类

目录 认识聚类算法 聚类算法API的使用 聚类算法实现流程 聚类算法模型评估 认识聚类算法 聚类算法是一种无监督的机器学习算法。 它将一组数据分成若干个不同的群组&#xff0c;使得每个群组内部的数据点相似度高&#xff0c;而不同群组之间的数据点相似度低。常用的相似…

OSU micro-benchmarks安装测试指导

OSU micro-benchmarks安装测试指导 OSU micro-benchmarks工具介绍 OSU Micro benchmark工具是由Ohio State University提供的MPI&#xff08;Message Passing Interface&#xff0c;消息传递接口&#xff09;通信效率评测工具。该工具旨在通过执行不同模式的MPI操作&#xff…

配置 IDEA 识别自定义规则的 Dockerfile 文件

目录 配置所在位置解决方案其他 配置所在位置 打开 IntelliJ IDEA&#xff0c;然后转到顶部菜单中的 “File” > “Settings”&#xff08;Windows/Linux&#xff09;或 “IntelliJ IDEA” > “Preferences”&#xff08;macOS&#xff09;。 在弹出的设置窗口中&#x…

LeetCode 125题:验证回文串

❤️❤️❤️ 欢迎来到我的博客。希望您能在这里找到既有价值又有趣的内容&#xff0c;和我一起探索、学习和成长。欢迎评论区畅所欲言、享受知识的乐趣&#xff01; 推荐&#xff1a;数据分析螺丝钉的首页 格物致知 终身学习 期待您的关注 导航&#xff1a; LeetCode解锁100…

VTK 数据类型:vtkUnstructuredGrid

VTK 数据类型&#xff1a;vtkUnstructuredGrid VTK 数据类型&#xff1a;vtkUnstructuredGridVTK 中数据类型的继承关系常用的几何类型实例&#xff1a;vtkHexahedron 和 vtkTetra VTK 数据类型&#xff1a;vtkUnstructuredGrid 非结构化点是在空间中离散随意分布的点&#xf…

【java-数据结构13-双向链表的增删查改1】

在上一篇文章中&#xff0c;我们已将双向链表成功创建&#xff0c;接下来&#xff0c;我们将对链表进行增删查改&#xff0c;敬请期待叭~&#xff08;觉得小编写的还可以的可以可以留个关注~&#xff09; &#xff08;1.遍历链表 思路&#xff1a;定义一个cur&#xff0c;让c…

使用Xshell工具连接ubuntu-方便快捷

使用Xshell连接ubuntu 在命令行输入 “sudo apt-get install openssh-server”安装openssh-server 开启 ssh-server&#xff0c;在命令行输入 “service ssh start”&#xff0c;然后输入密码即可

自动攻丝机进出料激光检测 进料出料失败报警循环手动及关闭报警退出无限循环

/**************进料检测********************/ /***缺料无限次循环 手动退出 超时报警*******/ void check_Pon() // { zstatus0; //报警计数器归零 Signauto1; …

使用ffmpeg将本地摄像头推流至RTSP服务器,支持RTSP和RTMP协议

一、流媒体传输协议&#xff1a;RTSP和RTMP 1、RTSP和RTMP的工作原理 1.1&#xff09;RTSP工作原理 用户设备向视频流平台发送RTSP请求。视频流平台返回可操作的请求列表&#xff0c;如播放、暂停等。用户设备发送具体的请求&#xff0c;如播放。视频流平台解析请求并启动相…

git仓库使用

git仓库是会限制空间大小限制的 git网络库的容量限制_github仓库大小限制-CSDN博客 git是用于管理github的工具 电脑左下角搜索git打开GitBash.exe 进入到要下载到本地的目录 下载到本地的文件不要更改&#xff01; 如果要使用请务必把文件复制到别的空间去再在这个别的空间…

数据库笔记-【视图】

视图 视图通俗是企业想展示给用户看的&#xff0c;数据库存储的数据有很多&#xff0c;但是也有很多是不能对外公开的&#xff0c;做项目的过程就通过视图这个媒介达到这种效果 视图也可以保证数据库表结构字段的隐私安全等 create or replace view stu_v_1 as select id st…

虚拟机有线已连接但无法上网—·可能性之一

背景 VMware虚拟机&#xff0c;搭建了三台Linux服务器&#xff0c;组成Hadoop集群&#xff0c;由于在Hadoop102上有一些经常与Mysql数据库交互的任务&#xff0c;需要经常打开运行&#xff0c;而Hadoop103和104则经常处于关闭状态&#xff0c;一段时间后再次启动集群时候&…