【C语言】指针概要

news/2024/11/25 18:55:15/

文章目录

  • 一、什么是指针
  • 二、指针类型
  • 三、野指针
  • 四、二级指针
  • 五、字符指针
  • 六、数组指针
    • 定义
    • 数组名
  • 七、函数指针

在这里插入图片描述

一、什么是指针

指针就是地址,口语中说的指针通常指的是指针变量。我们可以通过&(取地址操作符)取出变量的内存起始地址,把地址可以存放到一个变量中,这个变量就是指针变量。

一个指针变量多大?

  • 在32位的机器上,地址是32个0或者1组成二进制序列,那地址就得用4个字节的空间来存储,所以一个指针变量的大小就应该是4个字节。
  • 那如果在64位机器上,如果有64个地址线,那一个指针变量的大小是8个字节,才能存放一个地址。

二、指针类型

指针的定义方式是: **type + ***

char* 类型的指针是为了存放 char 类型变量的地址。
short* 类型的指针是为了存放 short 类型变量的地址。
int* 类型的指针是为了存放 int 类型变量的地址。

指针类型有什么意义呢?

1. 指针的类型决定了指针向前或者向后走一步有多大(距离)。

int main()
{int n = 10;char *pc = (char*)&n;int *pi = &n;printf("%p\n", &n);printf("%p\n", pc);printf("%p\n", pc+1);printf("%p\n", pi);printf("%p\n", pi+1);return  0;
}

在这里插入图片描述
由运行结果可以看出,char型指针加1向后走了1个字节,int型加1向后走了4个字节。

2. 指针的类型决定了,对指针解引用的时候有多大的权限(能操作几个字节)。

#include <stdio.h>
int main()
{int n = 0x11223344;char *pc = (char *)&n;int *pi = &n;*pc = 0;   //观察执行这两句时内存的变化*pi = 0;   return 0;
}

在这里插入图片描述

由结果可看出char* 的指针解引用只能访问一个字节,而 int* 的指针的解引用就能访问四个字节。

三、野指针

野指针就是指针指向的位置是不可知的(随机的、不正确的、没有明确限制的)

野指针出现的原因:

  1. 指针未初始化
#include <stdio.h>
int main()
{ int *p;//指针未初始化,默认为随机值return 0;
}
  1. 指针越界访问
#include <stdio.h>
int main()
{int arr[10] = {0};int *p = arr;int i = 0;for(i=0; i<=11; i++){//当指针指向的范围超出数组arr的范围时,p就是野指针*(p++) = i;}return 0;
}
  • 指针指向的空间释放

四、二级指针

指针变量也是变量,是变量就有地址,指针变量的地址被称为二级指针。
在这里插入图片描述

  • *pp 通过对pp中的地址进行解引用,这样找到的是 pa, *pp 其实访问的就是 p .
  • **pp 先通过 *pp 找到 p ,然后对 p 进行解引用操作: *p ,那找到的是 a

五、字符指针

在指针的类型中我们把char*这种指针类型称为为字符指针

char str1[]="Hellow world";
char str2[]="Hellow world";const char* str3="Hellow world";
const char* str4="Hellow world";

在这里插入图片描述

字符指针的一般使用方式为:

int main()
{char ch = 'w';char *pc = &ch;*pc = 'w';return 0;
}

还有另一种使用方式为:

int main()
{const char* pstr = "hello world.";//这一句代码意思是将首字符的地址放在了patr上,而不是把字符串printf("%s\n", pstr);return 0;
}

六、数组指针

定义

  • 指针数组:存放指针的数组
  • 数组指针:存放数组的地址
int* p1[10];//指针数组
int(*p2)[10];//数组指针

对于int* (p2) [10]
解释:p先和结合,说明p是一个指针变量,然后指着指向的是一个大小为10个整型的数组。所以p是一个指针,指向一个数组,叫数组指针。
这里要注意:[ ] 的优先级要高于 * 号的,所以必须加上()来保证p先和 * 结合。

数组名

int arr[10];

数组名通常表示数组首元素地址,两个情况例外:

  1. sizeof(数组名)
  2. &数组名
    这两种情况数组名表示整个数组
#include <stdio.h>
int main()
{int arr[10] = { 0 };printf("arr = %p\n", arr);printf("&arr= %p\n", &arr);printf("arr+1 = %p\n", arr+1);printf("&arr+1= %p\n", &arr+1);return 0;
}

在这里插入图片描述
从程序运行结果可以看出&arr和arr,虽然值是一样的,但是意义却不一样。
&arr 表示的是数组的地址,而不是数组首元素的地址
&arr 的类型是: int(*)[10] ,是一种数组指针类型
数组的地址+1,跳过整个数组的大小,所以 &arr+1 相对于 &arr 的差值是40

七、函数指针

#include <stdio.h>
void test()
{printf("Hwllow world");
}
int main()
{printf("%p\n", test);printf("%p\n", &test);return 0;
}

在这里插入图片描述
可以看出函数名也表示函数的地址,与&函数名一样,那么函数的地址存储到指针中应该如何表示呢

在这里插入图片描述

回调函数

回调函数就是一个通过函数指针调用的函数。如果你把函数的指针(地址)作为参数传递给另一个函数,当这个指针被用来调用其所指向的函数时,我们就说这是回调函数。回调函数不是由该函数的实现方直接调用,而是在特定的事件或条件发生时由另外的一方调用的,用于对该事件或条件进行响应。


http://www.ppmy.cn/news/775113.html

相关文章

Android面试题及答案3

Java Android面试题 JAVA相关基础知识 1、面向对象的特征有哪些方面 1.抽象&#xff1a; 抽象就是忽略一个主题中与当前目标无关的那些方面&#xff0c;以便更充分地注意与当前目标有关的方面。 抽象并不打算了解全部问题&#xff0c;而只是选择其中的一部分&#xff0c…

10年回顾:世界各地开发高手谈Java-Java基础-Java-编程开发

<script type"text/javascript"> google_ad_client "pub-8800625213955058"; /* 336x280, 创建于 07-11-21 */ google_ad_slot "0989131976"; google_ad_width 336; google_ad_height 280; // </script> <script type"t…

android 面试题(三)

JAVA相关基础知识 1、面向对象的特征有哪些方面 1.抽象&#xff1a; 抽象就是忽略一个主题中与当前目标无关的那些方面&#xff0c;以便更充分地注意与当前目标有关的方面。 抽象并不打算了解全部问题&#xff0c;而只是选择其中的一部分&#xff0c;暂时不用部分细节。抽…

RFT的对象识别技术

虽然目前在Watir的对象识别中(基于IEdev与Autoit)基本没有碰到识别问题,但该文章的介绍还是收获颇多,推荐! http://www.ibm.com/developerworks/cn/rational/r-cn-extendsrftobj/ 2008 年 2 月 28 日 长期困扰 Rational Functional Tester (RFT) 自动化测试的一个问题就是如何…

HTTP验证大法(Basic Auth,Session, JWT, Oauth, Openid)

成为一个"认证”老司机 本文翻译自Auth-Boss。 如果有翻译的不恰当或不对的地方&#xff0c; 欢迎指出。 成为一个认证老司机&#xff0c; 了解网络上不同的身份认证方法。 本文档的目的是记录和编目Web上的身份验证方法。认证指的是创建一个系统的过程&#xff0c;用户可…

传智博客(JavaWeb方面的所有知识)听课记录(经典)

一、 JavaWeb基础 第一天&#xff1a; 1&#xff0e;Eclipse详解&#xff1a; (1).Bad versionnumber in .class file&#xff1a;编译器版本和运行(JRE)版本不符合。高的JRE版本兼容低版本的编译器版本。 (2).当程序有错误的时候&#xff0c;使用Debug as 运行程序。双击…

认证 协议 JWT OAuth Session Cookie

本文翻译自Auth-Boss。 如果有翻译的不恰当或不对的地方&#xff0c; 欢迎指出。 成为一个认证老司机&#xff0c; 了解网络上不同的身份认证方法。 本文档的目的是记录和编目Web上的身份验证方法。认证指的是创建一个系统的过程&#xff0c;用户可以通过该系统“登录”在线服务…

记录的Android开发过程中遇到的问题。

180508 更新 网上下载demo 本地studio版本和demo版本不一致处理方式 修改两处 1 项目的build.gradle 里面classpath 2修改项目目录下 gradle-->wrapper-->gradle-wrapper.properties文件的 distributionUrl地址 然后 clean build rebuild 即可 1.在一个XML中能否使用…