当前位置: 首页 > news >正文

【C语言】指针的进阶(四)—— 企业笔试题解析

笔试题1:

int main()
{int a[5] = { 1, 2, 3, 4, 5 };int* ptr = (int*)(&a + 1);printf("%d,%d", *(a + 1), *(ptr - 1));return 0;
}

【答案】在x86环境下运行

【解析】

&a是取出整个数组的地址,&a就表示整个数组,因此 &a + 1就是跳过一整个数组指向数组后方,因为这是一个数组的地址,不能够直接赋值给整型指针,所以需要将该地址强制转换为整型指针,才能给指针ptr接收,此时指针ptr就指向了数组后方。

因此*(a+1)就等于a[1]自然是2,而*(ptr-1)就是向前挪动一个整型指向5


 

 笔试题2:

struct Test
{int Num;char* pcName;short sDate;char cha[2];short sBa[4];
}*p;
//假设p 的值为0x100000。 如下表表达式的值分别为多少?
//已知,结构体Test类型的变量大小是20个字节
//0x开头的数组是16进制的数字
int main()
{p = (struct Test*)0x100000;printf("%p\n", p + 0x1);printf("%p\n", (unsigned long)p + 0x1);printf("%p\n", (unsigned int*)p + 0x1);return 0;
}

【答案】在x86环境下运行

【解析】

%p:把要打印的数以地址的形式来打印。

  • p是结构体指针,p + 1 就是跳过一个结构体的大小即20个字节,又因为%p是以16进制地址形式打印,10进制的20等于16进制的14,因此结果为00100014。
  • p是结构体指针,被强制类型转换成unsigned long,整数+1就是+1,因此结果为00100001。
  • p是结构体指针,被强制类型转换成unsigned int*,在x86环境下,只要是指针大小就为4,那么指针+1就是跳过4个字节,因此结果为00100004。

 

笔试题3:

int main()
{int a[4] = { 1, 2, 3, 4 };int* ptr1 = (int*)(&a + 1);int* ptr2 = (int*)((int)a + 1);printf("%x,%x", ptr1[-1], *ptr2);return 0;
}

【答案】在x86环境下运行,小端存储

【解析】

该题涉及到大小端存储的问题,往期博客中有进行探讨,这里就不多赘述,如有兴趣或者不懂的可前往:点击前往

&a是取出整个数组的地址,&a就表示整个数组,因此 &a + 1就是跳过一整个数组指向数组后方,因为这是一个数组的地址,不能够直接赋值给整型指针,所以需要将该地址强制转换为整型指针,才能给指针ptr接收,此时指针ptr1就指向了数组后方。

ptr1[-1]等价于*(ptr1-1),表示ptr1向前挪动一个整型指向4,结果就为4

a被强制转换成int,即首元素地址被转换成int,整型+1就是+1。假设a的地址是0x100000,此时+1就等于0x100001,然后再强制类型转换为整型指针并赋值给ptr2。

*ptr2整型指针访问四个字节(即红框所框处),此时为内存存放的图解,需要转成真实值即0x02000000。


 

笔试题4:

int main()
{int a[3][2] = { (0, 1), (2, 3), (4, 5) };int* p;p = a[0];printf("%d", p[0]);return 0;
}

【答案】

【解析】

此题为细节题,过程不难。需要注意的是题中的是小括号,( , )即逗号表达式。a[3][2]中实际存储的是{1,3,5}。将a[0]赋值给p指针,即p指向数组第一行地址,再通过p[0]找到第一行第一个元素即1。


 

笔试题5:

int main()
{int a[5][5];int(*p)[4];p = a;printf("%p,%d\n", &p[4][2] - &a[4][2], &p[4][2] - &a[4][2]);return 0;
}

【答案】 

【解析】

a的类型是int (*) [5] ——— 即a指针指向一个大小为5的数组

p的类型是int (*) [4] ——— 即p指针指向一个大小为4的数组

当把a所指的地址赋值给指针p之后,a p指向同一地址,但是由于a认为自己指向的是5个元素,而p认为自己指向的是4个元素,这就会导致它们就算下标相同时访问到的内容也是不一样的,如图所示。

随着数组下标的增长,地址是由低到高的变化,并且指针和指针相减的绝对值得到的是指针之间的元素个数,而当取出p[4][2]和a[4][2]的地址之后相减,就是小地址减去大地址,得到一个负数,就是-4。

%p是打印地址,会认为内存中存储的补码就是地址,所以就是打印-4的补码

原码:10000000 00000000 00000000 00000100

反码:11111111  11111111  11111111   11111011

补码:11111111  11111111  11111111   11111100

以%p地址的形式打印补码转成16进制表示:FF FF FF FC

而-4以%d形式打印就是-4

对于原码反码补码的内容,往期博客有所提及,感兴趣的可以前往:立即前往


 

笔试题6:

int main()
{int aa[2][5] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };int* ptr1 = (int*)(&aa + 1);int* ptr2 = (int*)(*(aa + 1));printf("%d,%d", *(ptr1 - 1), *(ptr2 - 1));return 0;
}

【答案】

【解析】

  • &aa表示整个数组的地址,&aa+1跳过一整个二维数组,指向数组之后,再强制类型转换成整型指针赋值给ptr1。此时*(ptr1-1)就等于ptr1向前挪动一个整型并解引用找到10。
  • aa不是单独放在sizeof()内,因此aa表示首元素地址,aa又是二维数组,因此aa的首元素地址就是一个大小为5的数组,*(aa+1)等价于aa[1],表示aa跳过一个大小为5的数组指向下一个大小为5的数组再解引用找到该数组再赋值给整型指针ptr2。此时*(ptr2-1)就等于prt2向前挪动一个整型并解引用找到5。


 

 笔试题7:阿里巴巴笔试题

int main()
{char* a[] = { "work","at","alibaba" };char** pa = a;pa++;printf("%s\n", *pa);return 0;
}

【答案】

【解析】

a是一个字符指针数组,每个元素的类型都为char*。

pa是一个指向char*字符指针的指针,即二级指针。

pa++即是向前跳一个char*的大小,即指向a[1]的地址,*pa就是找到a[1]指向的元素at的首地址。


 

 笔试题8:

int main()
{char* c[] = { "ENTER","NEW","POINT","FIRST" };char** cp[] = { c + 3,c + 2,c + 1,c };char*** cpp = cp;printf("%s\n", **++cpp);printf("%s\n", *-- * ++cpp + 3);printf("%s\n", *cpp[-2] + 3);printf("%s\n", cpp[-1][-1] + 1);return 0;
}

【答案】

【解析】

本题是该篇博客中最难的一题,因为涉及到三级指针,并且还使用指针自增1自减1的方法去永久改变指针指向,会导致如果一步错,就会步步错的结局,因此需要非常仔细的去画图理解。

cpp存放char**类型的数据。 【** ++cpp】,cpp先自增1,跳过一个char**类型指向下一个元素的地址,如下图。

此时再对cpp进行解引用,找到cp[1],再解引用,找到c[2]即P的地址。此时%s打印出来就是POINT

 【* -- * ++cpp + 3】,加号优先级是最低的,所以最后算。cpp先自增1跳过一个char**大小指向下一个元素的地址,如下图。

此时再对cpp进行解引用,找到的是cp[2]即指向了c+1这块空间,再自减1则指向了c这块空间,再解引用找到了c[0]即ENTER中第一个E的地址,此时+3跳过三个char,最后指向ENTER中第二个E的地址,此时用%s打印出来就是ER

*cpp[-2] + 3】等价于【* *(cpp-2)+3】。与前面的cpp自增自减不同,cpp-2只是表达式并不会改变cpp的指向。

cpp[-2]指向cp[0],再解引用找到c[3],c[3]存放的是FIRST中F的地址,此时+3跳过三个字母指向FIRST中S的地址,再用%s打印出来就是ST

【 cpp[-1][-1] + 1】等价于【*(*(cpp-1) -1) + 1】。

*(cpp-1)找到c+2,c+2再-1就是c+1的地址,再进行解引用找到NEW中N的地址,再+1找到E的地址,此时用%s打印出来就是EW

 


 到此,这几道企业笔试题就讲解完成,希望能对你们有所帮助,也欢迎大家在评论区进行讨论。

如果觉得作者写的不错,求给博主一个大大的点赞支持一下,你们的支持是我更新的最大动力!

如果觉得作者写的不错,求给博主一个大大的点赞支持一下,你们的支持是我更新的最大动力!

如果觉得作者写的不错,求给博主一个大大的点赞支持一下,你们的支持是我更新的最大动力!

相关文章:

【C语言】指针的进阶(四)—— 企业笔试题解析

笔试题1: int main() {int a[5] { 1, 2, 3, 4, 5 };int* ptr (int*)(&a 1);printf("%d,%d", *(a 1), *(ptr - 1));return 0; } 【答案】在x86环境下运行 【解析】 &a是取出整个数组的地址,&a就表示整个数组,因此…...

博弈论——连续产量古诺模型

连续产量古诺模型 连续产量古诺模型是博弈论中非常经典的模型,以两厂商连续产量古诺博弈为例: 1、模型建立 Player:两个供应相同产品的厂商 产量:厂商1的产量为q1,厂商2的产量为q2,市场总供给为Qq1q2。…...

ROS2 驱动思岚G4雷达(ydlidar)- Rviz显示

记录G4雷达的配置 系统环境为:Ubuntu22.04 配置步骤 1、安装雷达SDK 2、构建 G4 雷达 ROS2 项目工程文件 3、使用Rviz可视化界面显示 1、安装雷达SDK 1.1 安装CMake YDLidar SDK需要CMake 2.8.2作为依赖项 Ubuntu 18.04或者Ubuntu 22.04 sudo apt install cmak…...

Spring Cloud Alibaba Sentinel流量防卫兵

文章目录 Spring Cloud Alibaba Sentinel流量防卫兵1. 分布式遇到的问题2.解决的方法 Sentinel: 分布式系统的流量防卫兵1. 简介和特折 Sentinel流量防卫兵的搭建1.引入依赖2.添加配置类3.运行类上添加SentinelResource,并配置blockHandler和fallback4. linux中放入…...

1.简单工厂模式

UML类图 代码 main.cpp #include <iostream> #include "OperationFactory.h" using namespace std;int main(void) {float num1;float num2;char operate;cin >> num1 >> num2 >> operate;Operation* oper OperationFactory::createOpera…...

GitHub Copilot Chat

9月21日&#xff0c;GitHub在官网宣布&#xff0c;所有个人开发者可以使用GitHub Copilot Chat。用户通过文本问答方式就能生成、检查、分析各种代码。 据悉&#xff0c;GitHub Copilot Chat是基于OpenAI的GPT-4模型打造而成&#xff0c;整体使用方法与ChatGPT类似。例如&…...

利用 QT 完成一个人脸识别系统,完成登录操作

1.配置文件 # Project created by QtCreator 2023-09-22T10:34:23 # #-------------------------------------------------QT core guigreaterThan(QT_MAJOR_VERSION, 4): QT widgetsTARGET project TEMPLATE appSOURCES main.cpp\widget.cppHEADERS widget.hFOR…...

MATLAB APP纯小白入门 两数相加

万事开头难&#xff0c;最怕第一次。使用matlab APP 实现两数求和&#xff0c;如下图所示&#xff0c;c a b&#xff0c;输入数字后&#xff0c;按 “” 就计算。 步骤 拖拽三个 Edit Field(Numeric) 过来&#xff0c;并且双击名字分别改为 a,b,c。注意修改名字后右边会有点变…...

ubuntu右上角的网络连接图标消失解决办法

ubuntu更新了几个文件后&#xff0c;我的ubuntu系统右上角的网络连接图标就消失了&#xff0c;然后怎么也找不到了&#xff0c;怎么办呢&#xff1f; 1、按快捷键ctrlaltt打开终端 2、按以下顺序输入如下的命令行 sudo service network-manager stop sudo rm /var/lib/Netw…...

conda创建虚拟环境安装aix360

目录 创建虚拟环境查看已有虚拟环境进入所创建的虚拟环境查看已安装的程序查看已安装的python模块配置镜像pipconda 安装aix360将环境添加到jupyter删除虚拟环境 创建虚拟环境 conda create -n aix360 python3.9查看已有虚拟环境 conda env list进入所创建的虚拟环境 activa…...

CentOS安装mariadb

1、 安装 [rootlocalhost ~]# yum install mariadb mariadb-server2、 启动并自启 [rootecs-3f21 ~]# systemctl enable mariadb –now3、 查看启动状态 [rootecs-3f21 ~]# systemctl status mariadb4、 初始化mariadb并设置root密码 [rootecs-3f21 ~]# mysql_secure_inst…...

FPGA——基础知识合集

文章目录 前言1、简述触发器与锁存器的区别2、简述 if-else 语句和 case 语句的区别3、相对 ARM、DSP 等处理器&#xff0c;谈谈 FPGA 具有哪些优势4、简述 Verilog 语句中阻塞赋值与非阻塞赋值的含义与区别&#xff0c;以及各自的适用的场景5、什么是同步电路&#xff0c;什么…...

【pytest】 标记冒烟用例 @pytest.mark.smoke

1. 使用 pytest.mark.smoke 标记用例 import pytest class Test_Smoke:def test_01(self):assert 112pytest.mark.smokedef test_02(self):assert 121pytest.mark.smokedef test_03(self):assert 1 2 3 2.配置文件pytest.ini [pytest] markers smoke 3. 运行指定标签 运…...

数据结构入门-14-排序

一、选择排序 1.1 选择排序思想 先把最小的元素拿出来 剩下的&#xff0c;再把最小的拿出来 剩下的&#xff0c;再把最小的拿出来 但是这样 空间复杂度是O(n) 优化一下&#xff0c;希望原地排序 1.1.2 选择原地排序 索引i指向0的位置 索引j指向i1的元素 j 后面的元素遍历&…...

Gin学习记录4——Controller和中间件

一. Controller 用不同的Controller可以实现业务的分类&#xff0c;不同类型的请求可以共用同一套中间件 1.1 单文件Controller 几乎等同于函数封装&#xff0c;直接将ctrl的代码写入到一个文件里然后调用&#xff1a; package adminimport ("net/http""git…...

FL Studio21.2中文版数字音乐制作软件

现在的FL也可以像splice一样啦&#xff0c;需要什么样的声音只需在fl里搜索&#xff0c;就会自动展示给你! FL Studio 简称FL&#xff0c;全称&#xff1a;Fruity Loops Studio&#xff0c;国人习惯叫它"水果"。软件现有版本是 FL Studio 21&#xff0c;已全面升级支…...

ELK 企业级日志分析系统 ELFK

目录 一、概述 二、组件介绍 2.1、ElasticSearch 2.2、Kiabana 2.3、Logstash 2.4、可以添加的其它组件&#xff1a;Filebeat 2.5、缓存/消息队列&#xff08;redis、kafka、RabbitMQ等&#xff09; 2.6、Fluentd 三、ELK工作原理 四、实例演示 1.ELK之 部署"E&q…...

IDEA中创建Java Web项目方法1

以下过程使用IntelliJ IDEA 2021.3 一、File-> New -> Project... 1. 项目类型中选择 Java Enterprise 项目 2. Name&#xff1a;填写自己的项目名称 3. Project template&#xff1a;选择项目的模板&#xff0c;Web application。支持JSP和Servlet的项目 4. Applica…...

源码:TMS FlexCel Studio for .NET 7.19

TMS FlexCel Studio for .NET 是100% 托管代码 Excel 文件操作引擎以及 Excel 和 PDF 报告生成&#xff0c;适用于 .NET、Xamarin.iOS、Xamarin.Android、Xamarin.Mac、Windows Phone 和 Windows Store 功能概述 使用 FlexCel Studio for .NET 创建可动态快速读写 Excel 文件的…...

多输入多输出 | MATLAB实现PSO-BP粒子群优化BP神经网络多输入多输出

多输入多输出 | MATLAB实现PSO-BP粒子群优化BP神经网络多输入多输出 目录 多输入多输出 | MATLAB实现PSO-BP粒子群优化BP神经网络多输入多输出预测效果基本介绍程序设计往期精彩参考资料 预测效果 基本介绍 Matlab实现PSO-BP粒子群优化BP神经网络多输入多输出预测 1.data为数据…...

mongodb源码分析session执行handleRequest命令find过程

mongo/transport/service_state_machine.cpp已经分析startSession创建ASIOSession过程&#xff0c;并且验证connection是否超过限制ASIOSession和connection是循环接受客户端命令&#xff0c;把数据流转换成Message&#xff0c;状态转变流程是&#xff1a;State::Created 》 St…...

视频字幕质量评估的大规模细粒度基准

大家读完觉得有帮助记得关注和点赞&#xff01;&#xff01;&#xff01; 摘要 视频字幕在文本到视频生成任务中起着至关重要的作用&#xff0c;因为它们的质量直接影响所生成视频的语义连贯性和视觉保真度。尽管大型视觉-语言模型&#xff08;VLMs&#xff09;在字幕生成方面…...

CMake 从 GitHub 下载第三方库并使用

有时我们希望直接使用 GitHub 上的开源库,而不想手动下载、编译和安装。 可以利用 CMake 提供的 FetchContent 模块来实现自动下载、构建和链接第三方库。 FetchContent 命令官方文档✅ 示例代码 我们将以 fmt 这个流行的格式化库为例,演示如何: 使用 FetchContent 从 GitH…...

今日科技热点速览

&#x1f525; 今日科技热点速览 &#x1f3ae; 任天堂Switch 2 正式发售 任天堂新一代游戏主机 Switch 2 今日正式上线发售&#xff0c;主打更强图形性能与沉浸式体验&#xff0c;支持多模态交互&#xff0c;受到全球玩家热捧 。 &#x1f916; 人工智能持续突破 DeepSeek-R1&…...

OPENCV形态学基础之二腐蚀

一.腐蚀的原理 (图1) 数学表达式&#xff1a;dst(x,y) erode(src(x,y)) min(x,y)src(xx,yy) 腐蚀也是图像形态学的基本功能之一&#xff0c;腐蚀跟膨胀属于反向操作&#xff0c;膨胀是把图像图像变大&#xff0c;而腐蚀就是把图像变小。腐蚀后的图像变小变暗淡。 腐蚀…...

2025季度云服务器排行榜

在全球云服务器市场&#xff0c;各厂商的排名和地位并非一成不变&#xff0c;而是由其独特的优势、战略布局和市场适应性共同决定的。以下是根据2025年市场趋势&#xff0c;对主要云服务器厂商在排行榜中占据重要位置的原因和优势进行深度分析&#xff1a; 一、全球“三巨头”…...

【C++特殊工具与技术】优化内存分配(一):C++中的内存分配

目录 一、C 内存的基本概念​ 1.1 内存的物理与逻辑结构​ 1.2 C 程序的内存区域划分​ 二、栈内存分配​ 2.1 栈内存的特点​ 2.2 栈内存分配示例​ 三、堆内存分配​ 3.1 new和delete操作符​ 4.2 内存泄漏与悬空指针问题​ 4.3 new和delete的重载​ 四、智能指针…...

ui框架-文件列表展示

ui框架-文件列表展示 介绍 UI框架的文件列表展示组件&#xff0c;可以展示文件夹&#xff0c;支持列表展示和图标展示模式。组件提供了丰富的功能和可配置选项&#xff0c;适用于文件管理、文件上传等场景。 功能特性 支持列表模式和网格模式的切换展示支持文件和文件夹的层…...

32单片机——基本定时器

STM32F103有众多的定时器&#xff0c;其中包括2个基本定时器&#xff08;TIM6和TIM7&#xff09;、4个通用定时器&#xff08;TIM2~TIM5&#xff09;、2个高级控制定时器&#xff08;TIM1和TIM8&#xff09;&#xff0c;这些定时器彼此完全独立&#xff0c;不共享任何资源 1、定…...

yaml读取写入常见错误 (‘cannot represent an object‘, 117)

错误一&#xff1a;yaml.representer.RepresenterError: (‘cannot represent an object’, 117) 出现这个问题一直没找到原因&#xff0c;后面把yaml.safe_dump直接替换成yaml.dump&#xff0c;确实能保存&#xff0c;但出现乱码&#xff1a; 放弃yaml.dump&#xff0c;又切…...