c语言进阶部分详解(指针进阶1)
大家好!指针的初阶内容我已经写好,可移步至我的文章:c语言进阶部分详解(指针初阶)_总之就是非常唔姆的博客-CSDN博客
基本内容我便不再赘述,直接带大家进入进阶内容:
目录
一.字符指针
1.讲解
2.例题
二.指针数组
1.讲解
2.练习
三.数组指针
1.数组指针的定义
2.数组指针与指针数组在语法上的对比
3.&数组名VS数组名
4.数组指针的使用
四.数组参数、指针参数
1.一维数组传参
2.二维数组传参
3.一级指针传参
4.二级指针传参
思考:当函数的参数为二级指针的时候,可以接收什么参数
一.字符指针
1.讲解
在指针的类型中我们知道有一种指针类型为字符指针 char* ;
其一般的使用场景为:这样
#include<stdio.h>
int main()
{char a = 'z';char* pa = &a;return 0;
}
还有这样:
int main()
{char* arr = "hello";printf("%s", arr);return 0;
}
针对char* arr = "hello";这个语句,特别容易让各位以为是把字符串 hello放到字符指针 arr 里了,但是本质是把字符串 hello首字符的地址放到了arr中
2.例题
下面来看一个例题加深理解:大家可以先思考一下再进行答案的比对
int main()
{char str1[] = "hello";char str2[] = "hello";const char* str3 = "hello";const char* str4 = "hello";if (str1 == str2)printf("str1 and str2 are same\n");elseprintf("str1 and str2 are not same\n");if (str3 == str4)printf("str3 and str4 are same\n");elseprintf("str3 and str4 are not same\n");return 0;
}
答案:
各位对了吗?
- 使用"=="运算符比较指针时,实际上比较的是指针所指向的地址是否相同,而不是比较字符串的内容是否相同
- 这里str3和str4指向的是一个同一个常量字符串。C/C++会把常量字符串存储到单独的一个内存区域,当几个指针。指向同一个字符串的时候,他们实际会指向同一块内存
- 用相同的常量字符串去初始化不同的数组的时候就会开辟出不同的内存块。所以str1和str2不同,str3和str4不同
二.指针数组
1.讲解
- 指针数组是一个数组,其中的每个元素都是指针。
- 它可以存储多个指针,每个指针可以指向不同类型的数据。
- 声明指针数组的语法为:type *ptr[size],其中type是指针指向的数据类型,size是数组的大小
示例:int num1 = 10, num2 = 20, num3 = 30;
int *ptr[3] = {&num1, &num2, &num3};
// 声明一个包含3个整型指针的数组
2.练习
用指针数组来模拟二维数组
int main()
{int arr1[4] = { 1,2,4,5 };int arr2[4] = { 2,2,5,5 };int arr3[4] = { 1,1,4,4 };int* pa[3] = { &arr1,&arr2,&arr3 };for (int i = 0; i < 3; i++){for (int j = 0; j < 4; j++){printf("%d ", pa[i][j]);}printf("\n");}return 0;
}
三.数组指针
1.数组指针的定义
- 数组指针是指向数组的指针变量。
- 它可以指向一个数组的首元素,也可以指向整个数组。
- 声明数组指针的语法为:type (*ptr)[size],其中type是数组元素的类型,size是数组的大小
示例:int arr[5] = {1, 2, 3, 4, 5};
int (*ptr)[5] = &arr; // 声明一个指向包含5个整数的数组的指针
2.数组指针与指针数组在语法上的对比
int *p1[10];
int (*p2)[10];
int (*p)[10];为数组指针
//解释:p先和*结合,说明p是一个指针变量,然后指着指向的是一个大小为10个整型的数组。所以p是一个指针,指向一个数组,叫数组指针。
//这里要注意:[]的优先级要高于*号的,所以必须加上()来保证p先和*结合int *p1[10];为指针数组
//解释:p先和[]结合,说明p是一个数组,然后数组的类型为int*
3.&数组名VS数组名
- &arr和arr,虽然值是一样的,但是意义应该不一样的
- &arr 表示的是数组的地址,而不是数组首元素的地址,数组的地址+1,跳过整个数组的大小
- 数组名是数组首元素的地址,但有两个例外:
1.sizeof(数组名),这里的数组名表示整个数组,sizeof(数组名)计算的是整个数组的大小,单位是字节。
2.&数组名,这里的数组名表示整个数组,取出的是数组的地址

4.数组指针的使用
void print_arr(int(*arr)[5], int row, int col)
{for (int i = 0; i < row; i++){for (int j = 0; j < col; j++){printf("%d ", arr[i][j]);}printf("\n");}
}
int main()
{int arr[3][5] = { 1,2,3,4,5,6,7,8,9,10 };//数组名arr,表示首元素的地址//但是二维数组的首元素是二维数组的第一行//所以这里传递的arr,其实相当于第一行的地址,是一维数组(有五个元素)的地址//可以数组指针来接收print_arr(arr, 3, 5);return 0;
}
- int arr[5]; arr是一个能够存放5个整型数据的数组
- int *parr1[10]; parr1是一个数组,数组有10个元素,每个元素的类型是int*
- int (*parr2)[10]; parr2是一个指针,该指针是指向数值的,指向的数组有10个元素,每个元素的类型是int
- int (*parr3[10])[5]; parr3是一个数组,是存放数组指针的数组,这个数组有10个元素,存放的这个数组指针指向的数组有5个元素,每个元素是int类型。
理解:parr3[10]可知是一个数组,int (* )[5]是一个数组指针类型,所以总的看是一个存放数组指针类型的数组。
四.数组参数、指针参数
1.一维数组传参
- 数组传参,形参是可以写成数组形式
- 数组传参的本质是传递了数组首元素的地址,形参也可以是指针
void test(int arr[])//可以 数组传参,形参是可以写成数组形式的
{}
void test(int arr[10])//可以
{}
void test(int* arr)//可以 数组传参的本质是传递了数组首元素的地址,形参也可以是指针
{}
void test2(int* arr[20])//可以
{}
void test2(int** arr)//可以 传过来的是int* 的地址,就用int**来接收
{}
int main()
{int arr[10] = { 0 };int* arr2[20] = { 0 };test(arr);test2(arr2);
}
2.二维数组传参
形参为二维数组或者数组指针
//总结:二维数组传参,函数形参的设计只能省略第一个[]的数字。
//因为对一个二维数组,可以不知道有多少行,但是必须知道一行多少元素。
//这样才方便运算。void test(int arr[3][5])//可以
{}
void test(int arr[][])//不可以:只能省略行,不能省略列
{}
void test(int arr[][5])//可以
{}void test(int* arr)//不可以
{}
void test(int* arr[5])//不可以
{}
void test(int(*arr)[5])//可以
{}
void test(int** arr)//不可以
{}
int main()
{int arr[3][5] = { 0 };test(arr);
}
3.一级指针传参
形参的部分写成一级指针就行了
void print(int* p, int sz) //形参的部分写成一级指针就行了
{int i = 0;for (i = 0; i < sz; i++){printf("%d\n", *(p + i));}
}
int main()
{int arr[10] = { 1,2,3,4,5,6,7,8,9 };int* pa = arr;int sz = sizeof(arr) / sizeof(arr[0]);//一级指针p,传给函数print(pa, sz);return 0;
}
4.二级指针传参
就用二级指针来接收
void test(int** ptr)
{printf("num = %d\n", **ptr);
}
int main()
{int n = 10;int* p = &n;int** pp = &p;test(pp);//传过来的是二级指针test(&p);return 0;
}
思考:当函数的参数为二级指针的时候,可以接收什么参数
只要是一级指针的地址就行:
int a=10;
int* p=&a;
int** pp=&p;
test(&p); test(pp);
int* arr[10]; 指针数组,首元素为一级指针,传过来首元素的地址
test(arr);
这次的内容梳理就先到这里了,我会加快更新后续内容的,感谢大家的支持!!!
相关文章:
c语言进阶部分详解(指针进阶1)
大家好!指针的初阶内容我已经写好,可移步至我的文章:c语言进阶部分详解(指针初阶)_总之就是非常唔姆的博客-CSDN博客 基本内容我便不再赘述,直接带大家进入进阶内容: 目录 一.字符指针 1.讲解…...
计算机竞赛 大数据商城人流数据分析与可视化 - python 大数据分析
0 前言 🔥 优质竞赛项目系列,今天要分享的是 🚩 基于大数据的基站数据分析与可视化 该项目较为新颖,适合作为竞赛课题方向,学长非常推荐! 🥇学长这里给一个题目综合评分(每项满分5分) 难度…...
各种电机驱动原理
步进电机 步进电机参考资料 野火官方文档 步进电机驱动原理 上面参考文档中有的内容就不写了,写一下我自己的总结吧。 说明: 电机驱动器输入信号有电机转动方向信号DIR,电机转速信号PWM,电机使能信号EN;电机驱动器…...
人脸图像数据增强
为什么要做数据增强 在计算机视觉相关任务中,数据增强(Data Augmentation)是一种常用的技术,用于扩展训练数据集的多样性。它包括对原始图像进行一系列随机或有规律的变换,以生成新的训练样本。数据增强的主要目的是增…...
Android 查看按键信息的常用命令详解
Android 查看按键信息的常用命令详解 文章目录 Android 查看按键信息的常用命令详解一、主要命令:二、命令详解1、getevent2、getevent -l3、dumsys input4、cat XXX.kl4、cat /dev/input/eventX5、getevent 其他命令6、input keyevent XX 三、简单示例修改四、总结…...
【Java 基础篇】Properties 结合集合类的使用详解
Java 中的 Properties 类是一个常见的用于管理配置信息的工具,它可以被看作是一种键值对的集合。虽然 Properties 通常用于处理配置文件,但它实际上也可以作为通用的 Map 集合来使用。在本文中,我们将详细探讨如何使用 Properties 作为 Map 集…...
数字孪生体标准编程
数字孪生体标准 括ISO TC184/SC4正在制定数字孪生制造标准ISO 23247、ISO/IEC JTC1/AG11正在推动数字孪生体标准、IEEE P2806正在做有关“数字表达”的标准。赢家通吃的标准战 卡尔夏皮罗和哈尔范里安撰写了《信息规则:网络经济战略指南》(Information R…...
力扣 -- 394. 字符串解码
解题方法: 参考代码: class Solution{ public:string decodeString(string s){stack<string> sst;stack<int> dst;//防止字符串栈为空的时候再追加字符串到栈顶元素sst.push("");int n s.size();int i 0;while(i<n)//最好不…...
面试官:什么是虚拟DOM?如何实现一个虚拟DOM?说说你的思路
🎬 岸边的风:个人主页 🔥 个人专栏 :《 VUE 》 《 javaScript 》 ⛺️ 生活的理想,就是为了理想的生活 ! 目录 一、什么是虚拟DOM 二、为什么需要虚拟DOM 三、如何实现虚拟DOM 小结 一、什么是虚拟DOM 虚拟 DOM (…...
Ubuntu安装中文拼音输入法
ubuntu安装中文拼音输入法 ubuntu版本为23.04 1、安装中文语言包 首先安装中文输入法必须要让系统支持中文语言,可以在 Language Support 中安装中文语言包。 添加或删除语音选项,添加中文简体,然后会有Applying changes的对话框&#x…...
高端知识竞赛中用到的软件和硬件有哪些
现在单位搞知识竞赛,已不满足于用PPT放题,找几个简单的抢答器、计分牌弄一下了,而是对现场效果和科技感要求更高了。大屏要分主屏侧屏,显示内容要求丰富炫酷;选手和评委也要用到平板等设备;计分要大气些&am…...
Vue 3.3 发布
本文为翻译 原文地址:宣布推出 Vue 3.3 |The Vue Point (vuejs.org) 今天我们很高兴地宣布 Vue 3.3 “Rurouni Kenshin” 的发布! 此版本侧重于开发人员体验改进 - 特别是 TypeScript 的 SFC <script setup> 使用。结合 Vue Language Tools&…...
算法|图论 3
LeetCode 130- 被围绕的区域 题目链接:力扣(LeetCode)官网 - 全球极客挚爱的技术成长平台 题目描述:给你一个 m x n 的矩阵 board ,由若干字符 X 和 O ,找到所有被 X 围绕的区域,并将这些区域…...
【数据结构】二叉树的层序遍历(四)
目录 一,层序遍历概念 二,层序遍历的实现 1,层序遍历的实现思路 2,创建队列 Queue.h Queue.c 3,创建二叉树 BTree.h BTree.c 4,层序遍历的实现 一,层序遍历概念 层序遍历:除了先序…...
macOS文件差异比较最佳工具:Beyond Compare 4
Beyond Compare for mac是一款Scooter Software研发的文件同步对比工具。你可以选择针对多字节的文本、文件夹、源代码,甚至是支持比对adobe文件、pdf文件或是整个驱动器,检查其文件大小、名称、日期等信息。你也可以选择使用Beyond Compare合并两个不同…...
Windows+Pycharm 如何创建虚拟环境
当我们开发一个别人的项目的时候,因为项目里有很多特有的包,比如 Pyqt5.我们不想破坏电脑上原来的包版本,这个时候,新建一个虚拟环境,专门针对这个项目就很有必要了. 简略步骤: 1.新建虚拟环境 1.打开 pycharm 终端(Terminal)安装虚拟环境工具: pip install virtualenv2.创…...
vant 按需导入 vue2
vant 按需导入 vue2 1、通过npm安装 # Vue 3 项目,安装最新版 Vant: npm i vant -S# Vue 2 项目,安装 Vant 2: npm i vantlatest-v2 -S2、自动按需引入组件 babel-plugin-import 是一款 babel 插件,它会在编译过程中…...
Java手写分治算法和分治算法应用拓展案例
Java手写分治算法和分治算法应用拓展案例 1. 算法思维导图 以下是用Mermanid代码表示的分治算法的实现原理: #mermaid-svg-nvJwIm97kPHEXQOR {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-nvJwIm97kP…...
学习 CodeWhisperer 的一些总结
目前一些常见的的 AI 工具 GitHub Copilot:GitHub 与 OpenAI 合作开发的一个人工智能助手。 Codeium:是一个免费的人工智能驱动的代码生成工具 Tabnine:一个自动代码生成工具,免费版本非常有限,只提供简短的代码完成…...
JavaScript 中的 `this` 指向问题与其在加密中的应用
JS中的 this 关键字是一个非常重要的概念,它在不同情况下会指向不同的对象或值。在本文中,我们将深入探讨 JavaScript 中 this 的各种情况,并思考如何将其应用于 JS加密中的一些有趣用途。 1. 全局上下文中的 this 在全局上下文中ÿ…...
国防科技大学计算机基础课程笔记02信息编码
1.机内码和国标码 国标码就是我们非常熟悉的这个GB2312,但是因为都是16进制,因此这个了16进制的数据既可以翻译成为这个机器码,也可以翻译成为这个国标码,所以这个时候很容易会出现这个歧义的情况; 因此,我们的这个国…...
Docker 离线安装指南
参考文章 1、确认操作系统类型及内核版本 Docker依赖于Linux内核的一些特性,不同版本的Docker对内核版本有不同要求。例如,Docker 17.06及之后的版本通常需要Linux内核3.10及以上版本,Docker17.09及更高版本对应Linux内核4.9.x及更高版本。…...
在软件开发中正确使用MySQL日期时间类型的深度解析
在日常软件开发场景中,时间信息的存储是底层且核心的需求。从金融交易的精确记账时间、用户操作的行为日志,到供应链系统的物流节点时间戳,时间数据的准确性直接决定业务逻辑的可靠性。MySQL作为主流关系型数据库,其日期时间类型的…...
ES6从入门到精通:前言
ES6简介 ES6(ECMAScript 2015)是JavaScript语言的重大更新,引入了许多新特性,包括语法糖、新数据类型、模块化支持等,显著提升了开发效率和代码可维护性。 核心知识点概览 变量声明 let 和 const 取代 var…...
《从零掌握MIPI CSI-2: 协议精解与FPGA摄像头开发实战》-- CSI-2 协议详细解析 (一)
CSI-2 协议详细解析 (一) 1. CSI-2层定义(CSI-2 Layer Definitions) 分层结构 :CSI-2协议分为6层: 物理层(PHY Layer) : 定义电气特性、时钟机制和传输介质(导线&#…...
最新SpringBoot+SpringCloud+Nacos微服务框架分享
文章目录 前言一、服务规划二、架构核心1.cloud的pom2.gateway的异常handler3.gateway的filter4、admin的pom5、admin的登录核心 三、code-helper分享总结 前言 最近有个活蛮赶的,根据Excel列的需求预估的工时直接打骨折,不要问我为什么,主要…...
屋顶变身“发电站” ,中天合创屋面分布式光伏发电项目顺利并网!
5月28日,中天合创屋面分布式光伏发电项目顺利并网发电,该项目位于内蒙古自治区鄂尔多斯市乌审旗,项目利用中天合创聚乙烯、聚丙烯仓库屋面作为场地建设光伏电站,总装机容量为9.96MWp。 项目投运后,每年可节约标煤3670…...
【HTML-16】深入理解HTML中的块元素与行内元素
HTML元素根据其显示特性可以分为两大类:块元素(Block-level Elements)和行内元素(Inline Elements)。理解这两者的区别对于构建良好的网页布局至关重要。本文将全面解析这两种元素的特性、区别以及实际应用场景。 1. 块元素(Block-level Elements) 1.1 基本特性 …...
[Java恶补day16] 238.除自身以外数组的乘积
给你一个整数数组 nums,返回 数组 answer ,其中 answer[i] 等于 nums 中除 nums[i] 之外其余各元素的乘积 。 题目数据 保证 数组 nums之中任意元素的全部前缀元素和后缀的乘积都在 32 位 整数范围内。 请 不要使用除法,且在 O(n) 时间复杂度…...
【SpringBoot自动化部署】
SpringBoot自动化部署方法 使用Jenkins进行持续集成与部署 Jenkins是最常用的自动化部署工具之一,能够实现代码拉取、构建、测试和部署的全流程自动化。 配置Jenkins任务时,需要添加Git仓库地址和凭证,设置构建触发器(如GitHub…...
