C语言-指针初学速成

1.指针是什么

C语言指针是一种特殊的变量,用于存储内存地址。它可以指向其他变量或者其他数据结构,通过指针可以直接访问或修改存储在指定地址的值。指针可以帮助我们在程序中动态地分配和释放内存,以及进行复杂的数据操作。在C语言中,指针操作是一项重要的基本操作,掌握指针的使用对于编写高效的C语言程序非常重要。

说通俗点:

1.指针是内存中一个最小单元的编号,也就是地址2.平时口语中说的指针,通常指的是指针变量,是用来存放内存地址的变量总结:指针就是地址,口语中说的指针通常指的是指针变量。(把内存单元的编号就称为地址(地址也叫指针)指针其实就是地址,地址就是编号指针就是内存单元的编号)

指针和指针变量:

    

2.指针和指针类型

  • int p; -- 这是一个普通的整型变量
  •  int *p; -- 首先从 p 处开始,先与 * 结合,所以说明 p 是一个指针, 然后再与 int 结合, 说明指针所指向的内容的类型为 int 型。所以 p 是一个返回整型数据的指针。
  •  int p[3] -- 首先从 p 处开始,先与 [] 结合,说明 p 是一个数组, 然后与 int 结合, 说明数组里的元素是整型的, 所以 p 是一个由整型数据组成的数组。
  •  int *p[3]; -- 首先从 p 处开始, 先与 [] 结合,因为其优先级比 * 高,所以 p 是一个数组, 然后再与 * 结合, 说明数组里的元素是指针类型, 然后再与 int 结合, 说明指针所指向的内容的类型是整型的, 所以 p 是一个由返回整型数据的指针所组成的数组。
  •  int (*p)[3]; -- 首先从 p 处开始, 先与 * 结合,说明 p 是一个指针然后再与 [] 结合(与"()"这步可以忽略,只是为了改变优先级), 说明指针所指向的内容是一个数组, 然后再与int 结合, 说明数组里的元素是整型的。所以 p 是一个指向由整型数据组成的数组的指针。
  •  int **p; -- 首先从 p 开始, 先与 * 结合, 说是 p 是一个指针, 然后再与 * 结合, 说明指针所指向的元素是指针, 然后再与 int 结合, 说明该指针所指向的元素是整型数据。由于二级指针以及更高级的指针极少用在复杂的类型中, 所以后面更复杂的类型我们就不考虑多级指针了, 最多只考虑一级指针。
  •  int p(int); -- 从 p 处起,先与 () 结合, 说明 p 是一个函数, 然后进入 () 里分析, 说明该函数有一个整型变量的参数, 然后再与外面的 int 结合, 说明函数的返回值是一个整型数据。
  •  int (*p)(int); -- 从 p 处开始, 先与指针结合, 说明 p 是一个指针, 然后与()结合, 说明指针指向的是一个函数, 然后再与()里的 int 结合, 说明函数有一个int 型的参数, 再与最外层的 int 结合, 说明函数的返回类型是整型, 所以 p 是一个指向有一个整型参数且返回类型为整型的函数的指针。
  •  int *(*p(int))[3]; -- 可以先跳过, 不看这个类型, 过于复杂从 p 开始,先与 () 结合, 说明 p 是一个函数, 然后进入 () 里面, 与 int 结合, 说明函数有一个整型变量参数, 然后再与外面的 * 结合, 说明函数返回的是一个指针, 然后到最外面一层, 先与[]结合, 说明返回的指针指向的是一个数组, 然后再与 * 结合, 说明数组里的元素是指针, 然后再与 int 结合, 说明指针指向的内容是整型数据。所以 p 是一个参数为一个整数据且返回一个指向由整型指针变量组成的数组的指针变量的函数。


3. 尚未初始化的指针的含义

未初始化的指针变量就是“野”指针,它指向的是无效的地址。
出现野指针最典型的情形就是在定义指针变量之后没有对它进行初始化

指针指向某个对象之后,当这个对象的生命周期已经结束,对象已经消亡后,仍使用指针访问该对象,将出现运行时错误。考察如下程序。

#include <stdio.h>
int main(){
int*p;//指针未初始化,默认就是随机值printf("p=%d\n",*p);
//p是一个野指针,现在给他赋值可能会把它指向的内存区域数据破坏//会出现原本有用的内存数据被打乱 了。
*p=10;
printf("p=%d\n",*p);      return 0;

4. 指针运算

指针运算是针对指针(变量存储地址的变量)进行的运算操作。在程序中,指针可以通过加减操作来改变其值,这种操作就是指针运算。常见的指针运算有以下几种:

  1. 指针加法运算:可以将指针的值增加或减少若干个单位。例如,p + n 表示指针 p 的值增加 n 个单位,而 p - n 则表示指针 p 的值减少 n 个单位。

  2. 指针的自增和自减运算:可以将指针的值增加或减少一个单位。例如,p++ 表示指针 p 的值增加一个单位,而 p-- 则表示指针 p 的值减少一个单位。

  3. 指针的比较运算:可以比较两个指针的大小关系。例如,p1 > p2 表示指针 p1 的值大于指针 p2 的值,而 p1 < p2 则表示指针 p1 的值小于指针 p2 的值。

指针运算在许多编程语言中都是一种常见的操作,它可以用于实现数组、链表等数据结构,也可以用于动态内存分配和管理。但是需要注意的是,在进行指针运算时,要保证指针所指向的内存单元是有效的,否则可能会导致程序出现错误。

例1


5.指针和数组

指针与数组的关系

 1.当一个指针变量被初始化成数组名时,就说该指针变量指向了数组。如:

ptr被置为数组str的第一个元素的地址,因为数组名就是该数组的首地址,也是数组第一个元素的地址。此时可以认为指针ptr就是数组str(反之不成立),这样原来对数组的处理都可以用指针来实现。如对数组元素的访问,既可以用下标变量访问,也可以用指针访问。

2.指向数组元素的指针

  若有如下定义:

则pa=&a[0]是将数组第1个元素的地址赋给了指针变量pa。

实际上,C语言中数组名就是数组的首地址,所以第一个元素的地址可以用两种方法获得:pa=&a[0]或pa=a。

这两种方法在形式上相像,其区别在于:pa是指针变量,a是数组名。值得注意的是:pa是一个可以变化的指针变量,而a是一个常数。因为数组一经被说明,数组的地址也就是固定的,因此a是不能变化的,不允许使用a++、++a或语句a+=10,而pa++、++pa、pa+=10则是正确的。由此可见,此时指针与数组融为一体。

    例2

数组a中元素用下标表示为:
int *p = a;
*p,*(p+1),*(p+2),*(p+3),*(p+4)

①既然p是指向数组第一个元素起始地址的指针,可以用*(p+I)表示数组中第1+1个元索,a也是指向数组第一个元素的指针啊,那么能不能用*(a+1)表示第1+1个元素呢?
可以的,可以用printf 打印 *(a+i)的值验证
(②)反过来,a是指向数组第一个元素起始地址的指针,可以用a加数组下标引用数组元素,如a[3],p也是指向数组第一个元素起始地址的指
能不能用p加数组下标引用数组元素?计,也是可以的,可以用printf 打印 p[0],p[1]....的值验证PS: 由上得,数组名a和指针p是一样的。实际上编译时,数组元素a[i] 就是当作*(a+i)去处理的,先通过数组名a找到数组的首地址,然后首地址 a+i 得到元素a[i]的地址,
再然后通过*(a+i)得到第1个元素的内容。
所以:数组的第!个元索直接写成*(a+1)的形式直接取得值,效率不就提升了吗。省去编译器先通过数组名a找到数组的首地址,然后首地址 a+i 得到元素a[i]的地址,
再然后通过*(a+1)得到第1个元素的内容

6.二级指针

指针 可以指向一份普通类型的数据,例如 int、double、char 等,也可以指向一份指针类型的数据,例如 int *、double *、char * 等。 如果一个指针指向的是另外一个指针,我们就称它为 二级指针 ,或者 指向指针的指针 。


 

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

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

【算法分析与设计】1的个数

&#x1f4dd;个人主页&#xff1a;五敷有你 &#x1f525;系列专栏&#xff1a;算法分析与设计 ⛺️稳中求进&#xff0c;晒太阳 题目 编写一个函数&#xff0c;输入是一个无符号整数&#xff08;以二进制串的形式&#xff09;&#xff0c;返回其二进制表达式中数字位…

钧达股份:光伏跨界新贵只身赴港股,光伏“秩序重塑”?

2月21日&#xff0c;钧达股份终是在“千呼万唤”之中披露最新业绩快报。 快报显示&#xff0c;钧达股份预计2023年经调整后营业收入183.97亿元&#xff0c;同比增长58.65%&#xff0c;归母净利润8.32亿元&#xff0c;同比增长16.00%。 其中&#xff0c;由于Q4完整计提了9.5GW…

洛谷 【算法1-2】排序

【算法1-2】排序 - 题单 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn) 鄙人不才&#xff0c;刷洛谷&#xff0c;迎蓝桥&#xff0c;【算法1-2】排序 已刷&#xff0c;现将 AC 代码献上&#xff0c;望有助于各位 P1271 选举学生会 【深基9.例1】选举学生会 - 洛谷 题目 解答…

概率密度函数(PDF)与神经网络中的激活函数

原创:项道德(daode3056,daode1212) 在量子力学中&#xff0c;许多现象都是统计的结果&#xff0c;基本上用的是正态分布&#xff0c;然而&#xff0c;从本质上思考&#xff0c;应该还存在低阶的分布&#xff0c;标准的正态分布是它的极限&#xff0c;这样一来&#xff0c;或许在…

《论文阅读》通过识别对话中的情绪原因来提高共情回复的产生 EMNLP 2021

《论文阅读》通过识别对话中的情绪原因来提高共情回复的产生 EMNLP 2021 前言简介方法实现Emotion ReasonerResponse Generator实验结果示例总结前言 亲身阅读感受分享,细节画图解释,再也不用担心看不懂论文啦~ 无抄袭,无复制,纯手工敲击键盘~ 今天为大家带来的是《Improv…

备战蓝桥杯—— 双指针技巧巧答链表1

对于单链表相关的问题&#xff0c;双指针技巧是一种非常广泛且有效的解决方法。以下是一些常见问题以及使用双指针技巧解决&#xff1a; 合并两个有序链表&#xff1a; 使用两个指针分别指向两个链表的头部&#xff0c;逐一比较节点的值&#xff0c;将较小的节点链接到结果链表…

【ECharts】调用接口获取后端数据的四种方法

使用eacharts做大屏&#xff0c;需要使用后端数据&#xff0c;下面的方法是自己试过有效的&#xff0c;有什么不对的&#xff0c;望各位大佬指点。 目录 方法一&#xff1a;在mounted中使用定时器调用eacharts方法&#xff08;定时器可以获取到data中的数据&#xff09; 方法…

图解李白的“朋友圈”

《长安三万里》作为2023年票房第一的国漫电影&#xff0c;以安史之乱为背景&#xff0c;从诗人高适的视角铺设了一幅绚丽的历史长卷&#xff0c;细细讲述“诗仙”李白跌宕起伏的一生&#xff0c;以及大唐盛世一路荣耀幻灭的唏嘘。同时&#xff0c;在这部动画电影中出现了多位大…

CP04大语言模型ChatGLM3-6B特性代码解读(2)

CP04大语言模型ChatGLM3-6B特性代码解读&#xff08;2&#xff09; 文章目录 CP04大语言模型ChatGLM3-6B特性代码解读&#xff08;2&#xff09;构建对话demo_chat.py定义client对象与LLM进行对话 构建工具调用demo_tool.py定义client对象定义工具调用提示词定义main&#xff0…

接口测试需求分析

测试接口的时候&#xff0c;可能很多人都会想&#xff0c;按着研发给的接口协议文档来测&#xff0c;不就好了吗&#xff1f; 其实&#xff0c;对于接口的测试&#xff0c;还需要有点深度的需求分析&#xff0c;然后再进行对应的测试。对于接口测试&#xff0c;这里有个不太详…

利用nginx内部访问特性实现静态资源授权访问

在nginx中&#xff0c;将静态资源设为internal&#xff1b;然后将前端的静态资源地址改为指向后端&#xff0c;在后端的响应头部中写上静态资源地址。 近期客户对我们项目做安全性测评&#xff0c;暴露出一些安全性问题&#xff0c;其中一个是有些静态页面&#xff08;*.html&…

Android 开发一个耳返程序(录音,实时播放)

本文目录 点击直达 Android 开发一个耳返程序程序编写1. 配置 `AndroidManifast.xml`2.编写耳返管理器3. 录音权限申请4. 使用注意最后我还有一句话要说怕相思,已相思,轮到相思没处辞,眉间露一丝Android 开发一个耳返程序 耳返程序是声音录入设备实时播放的一种程序,理论上…

XFF伪造 [MRCTF2020]PYWebsite1

打开题目 直接查看源码 看到一个./flag.php 访问一下 购买者的ip已经被记录&#xff0c;本地可以看到flag&#xff0c;那么使用xff或者client-ip伪造一下ip试试 bp抓包 加一个X-Forwarded-For头 得到flag

关于git子模块实践(一)

背景 在日常项目开发中&#xff0c;随着项目的迭代&#xff0c;不可避免的是主项目会引入到很多三方库&#xff0c;或者自研的一些模块。有一种场景&#xff0c;就是这些模块&#xff0c;是随着开发而进行迭代&#xff0c;且多个项目公用的&#xff0c;这种情况&#xff0c;在…

探讨javascript中运算符优先级

如果阅读有疑问的话&#xff0c;欢迎评论或私信&#xff01;&#xff01; 本人会很热心的阐述自己的想法&#xff01;谢谢&#xff01;&#xff01;&#xff01; 文章目录 深入理解JavaScript运算符优先级运算符优先级概述示例演示示例1&#xff1a;加法和乘法运算符的优先级示…

86、移除推理路径上的所有内存操作

动态申请内存的影响,前两节已经介绍过了,细心的朋友可能会发现,在使用 C++实现的 resnet50 代码中,还存在一处动态申请内存的操作。 那就是对于每一层的输入或输出 feature map 数据进行内存申请,比如在 3rd_preload/ops/conv2d.cc 文件中,卷积的计算中存在对于输出 fea…

MaxScale实现mysql8读写分离

MaxScale 实验环境 中间件192.168.150.24MaxScale 22.08.4主服务器192.168.150.21mysql 8.0.30从服务器192.168.150.22mysql 8.0.30从服务器192.168.150.23mysql 8.0.30 读写分离基于主从同步 1.先实现数据库主从同步 基于gtid的主从同步配置 主库配置 # tail -3 /etc/my.…

Aigtek电压放大器的应用场合有哪些

电压放大器是一种主要用于信号处理的重要电子设备&#xff0c;它可以将输入的低电压信号放大到较高的输出电压水平。在各个应用领域中&#xff0c;电压放大器发挥着重要的作用。下面西安安泰点击将介绍电压放大器的应用场合。 通信系统&#xff1a;电压放大器在通信系统中具有重…

ant-design-charts 对带缩略轴柱状图 根据数据自定义列处理, 以颜色为例

摘要 本文主要对ant-design-charts中带缩略柱状图进行自定义列处理 ant-design-charts版本&#xff1a;1.4.2 1、定义数据 const data1 [{"a": "七台河","b": 52827.32,c: 2},{"a": "万县","b": 20000,c: 1},…

队列的基本操作——常见队列的对比分析(c语言完整代码包含注释)

目录 一、队列 1.1基本概念 1.2基本操作 1.3 队列分类 1.3.1带头队列 1.3.2不带头队列 1.3.3 循环带头队列 1.3.4 循环不带头队列 1.3.5 总结 二、代码实现 2.1带头队列 2.2不带头队列 2.3循环带头队列 2.4循环不带头队列 一、队列 1.1基本概念 队列&#xff08…