初阶指针的介绍

news2024/11/15 21:53:39

 


文章目录

  •  指针是什么
  •  指针和指针类型 
  • 野指针 
  • 指针运算 
  • 指针和数组 
  • 二级指针
  • 指针数组

 


一、 指针是什么

指针理解的2个要点:

        1. 指针是内存中一个最小单元的编号,也就是地址

        2. 平时口语中说的指针,通常指的是指针变量,是用来存放内存地址的变量

总结:指针就是地址,口语中说的指针通常指的是指针变量。

指针变量

我们可以通过 & (取地址操作符)取出变量的内存其实地址,把地址可以存放到一个变量中,这个
变量就是指针变量。
#include <stdio.h>

int main()
{
	int a = 10;//在内存中开辟一块空间
	int* p = &a;//这里我们对变量a,取出它的地址,可以使用&操作符。
	   //a变量占用4个字节的空间,这里是将a的4个字节的第一个字节的地址存放在p变量中,p就是一个之指针变量。
	return 0;
}
总结:
        指针变量,用来存放地址的变量。(存放在指针中的值都被当成地址处理)。
         指针是用来存放地址的,地址是唯一标示一块地址空间的。
        指针的大小在32 位平台是 4 个字节,在 64 位平台是 8 个字节。

二、指针和指针类型

#include<stdio.h>

int main()
{
	int a = 0x11223344;
	int * pa = &a;
	//char* pa = &a;
	*pa = 0;
	return 0;
}

 

#include<stdio.h>

int main()
{
	int a = 10;
	int* pa = &a;
	char* pc = &a;

	printf("%p\n", pa);
	printf("%p\n", pc);

	printf("%p\n", pa + 1);
	printf("%p\n", pc + 1);

	return 0;
}

 

 

#include<stdio.h>

int main()
{
	int arr[10] = { 0 };

	//如果希望按照一个整数的形式访问
	int* p = arr;
	int i = 0;
	for (i = 0; i < 10; i++) {
		*p = 0x11223344;
		p++;
	}

	//假设你希望,你访问这个40个字节的时候,是以字节为单位访问
	char* p = (char*)arr;
	int i = 0;
	for (i = 0; i < 40; i++)
	{
		*p = 'x';
		p++;

	}
	return 0;
}

注意:

         指针的类型决定了,对指针解引用的时候有多大的权限(能操作几个字节)。
        比如: char* 的指针解引用就只能访问一个字节,而 int* 的指针的解引用就能访问四个字节。

三、野指针

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

野指针成因

1. 指针未初始化

#include <stdio.h>

int main()
{ 
     int *p;//局部变量指针未初始化,默认为随机值
     *p = 20;
     return 0;
}

2.指针越界访问

#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;
}

3. 指针指向的空间释放

#include<stdio.h>

int* test()
{
	int a = 10;
	printf("%d\n", a);
	return& a;
}

int main()
{
	int* p = test();
	*p = 100;

	return 0;
}

 规避野指针的方式:

1. 指针初始化
2. 小心指针越界
3. 指针指向空间释放即使置NULL
4. 避免返回局部变量的地址
5. 指针使用之前检查有效性

四、指针运算

指针+-整数

#define N_VALUES 5
float values[N_VALUES];
float *vp;
//指针+-整数;指针的关系运算
for (vp = &values[0]; vp < &values[N_VALUES];)
{
     *vp++ = 0;
}

指针-指针

int my_strlen(char *s)
{
       char *p = s;
       while(*p != '\0' )
              p++;
       return p-s;
}

注意:

        指针-指针是两个指针必须指向同一块空间,得到的是指针和指针之间元素的个数。

指针的关系运算

for(vp = &values[N_VALUES-1]; vp >= &values[0];vp--)
{
    *vp = 0;
}

标准规定:

        允许指向数组元素的指针与指向数组最后一个元素后面的那个内存位置的指针比较,但是不允许与 指向第一个元素之前的那个内存位置的指针进行比较。

五、指针和数组

#include <stdio.h>

/*int main()
{
	int arr[10] = { 1,2,3,4,5,6,7,8,9,0 };
	printf("%p\n", arr);
	printf("%p\n", &arr[0]);
	return 0;
}*/

int main()
{
	int arr[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 0 };
	int* p = arr; //指针存放数组首元素的地址
	int sz = sizeof(arr) / sizeof(arr[0]);
	int i = 0;
	for (i = 0; i < sz; i++)
	{
		printf("%d ", *(p + i));
	}
	return 0;
}

六、二级指针

指针变量也是变量,是变量就有地址

#include<stdio.h>

int main()
{
	int a = 10;
	int* pa = &a;//pa是指针变量(一级指针)

	int* ppa = &pa;//ppa是二级指针
	return 0;
}

对于二级指针的运算有:

        *ppa 通过对ppa中的地址进行解引用,这样找到的是 pa *ppa 其实访问的就是 pa .

int b = 20 ;
* ppa = & b ; // 等价于 pa = &b;

**ppa 先通过 *ppa 找到 pa ,然后对 pa 进行解引用操作: *pa ,那找到的是 a .

** ppa = 30 ;
// 等价于 *pa = 30;
// 等价于 a = 30;

七、指针数组

指针数组:存放指针的数组。
int arr1 [ 5 ];
char arr2 [ 6 ];

 

 

int* arr3 [ 5 ];
arr3 是一个数组,有五个元素,每个元素是一个整形指针。

 

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

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

相关文章

达梦8数据库优化

1.什么是执行计划&#xff1f; 一条SQL语句在数据库中执行过程或访问路径的描述。 2.如何查看达梦数据库执行计划&#xff1f; 通过explain命令&#xff1a; EXPLAIN 执行的SQL语句&#xff0c;如 SQL> EXPLAIN SELECT * FROM TEST1; 1 #NSET2: [1, 1113, 602] 2 …

Vue笔记01 模板语法,数据代理,事件处理,计算监听属性,绑定样式,列表渲染,数据监测

基本使用 引入vue 创建vue实例并关联容器 一个Vue实例只应对应一个容器 一个Vue实例可以有多个组件 模板语法 使用Vue实例中数据 root容器中代码被称为vue模板 语法分为插值语法和指令(v-xxx) 插值语法 绑定标签体内容 {{}}中的可以是js表达式&#xff08;特殊的js代码&…

CF790 div4 F(双指针) H(逆序对)

乐&#xff0c;被div4薄纱了没想到把所有出现次数>k的数放一个数组里然后双指针还有H&#xff0c;连逆序对都没看出来&#xff0c;嘻感觉以后还是写写div4算了&#xff0c;写什么div2啊&#xff0c;caibiProblem - F - Codeforces题意&#xff1a;给定一个数列&#xff0c;长…

2023万象更新!smardaten企业级无代码新版本也来啦!

2022可以说是在反复的做核酸、查绿码中度过的&#xff0c;不曾想年终一个月还是躲不过“小阳人”的命运。而这一个月&#xff0c;研发部的“阳过”们依旧加班加点给我们带来了最新版本——V8R4C70。在2022-2023跨年之际&#xff0c;smardaten这次又有哪些新的变化呢&#xff0c…

MVC三层架构的模式

大家好&#xff0c;今天给大家分享一下MVC 三层架构的模式 首先你要知道&#xff0c;所谓的MVC就是一种面向于javaee企业级开发的设计模式 这里要强调一点,MVC 不是一种技术&#xff0c;不是一种像spring 那样的框架&#xff0c;它是一种思想&#xff08;可以理解为一种解决问…

【GNSS算法工程入门】1. Git入门

写在前面笔者在GNSS算法开发岗位从业过一段时间&#xff0c;和大部分同学类似&#xff0c;在GNSS开发过程中&#xff0c;也是从工程化的小白逐渐成长起来。而在算法开发从业的过程中&#xff0c;发现有些基础的知识其实在学校学习过程中是相对缺失的。麻省理工有个课程叫计算机…

编译型语言的Docker镜像构建小技巧

最近公司需要将一个底层服务打包成docker镜像&#xff0c;作为征战docker一年的小白当然不能错过这次练手的好机会。简单介绍一下这个项目&#xff1a;该项目为一个纯restful风格的后端项目&#xff0c;后端由java开发、worker节点由python开发、管理员使用的命令行工具由rust开…

wpa_supplicant EAP状态机分析

EAP状态机分析RFC4137协议状态机设计原理模块划分SM状态定义SM状态转换SM使用到的变量及函数定义变量1.SM与LL交互使用到的变量列表2.SM与EM交互使用到的变量3.SM内部使用的变量函数wpas代码RFC4137协议 RFC4137&#xff1a;“State Machine for Extensible Authentication Pr…

强化学习笔记-01多臂老虎机问题

本文是博主对《Reinforcement Learning- An introduction》的阅读笔记&#xff0c;不涉及内容的翻译&#xff0c;主要为个人的理解和思考。 1. 多臂老虎机问题 多臂老虎机问题是指存在K个老虎机&#xff0c;每个老虎机的获胜金额是一个未知的概率分布且相互独立&#xff0c;假设…

一文解决Opencv四大经典算子——sobel算子、scharr算子、laplacian算子、canny算子

Opencv四大算子 Sobel算子Scharr算子laplacian算子canny算子总结边缘是像素值发生跃迁的位置,是图像的显著特征之一,在图像特征提取,对象检测,模式识别等方面都有重要的作用! Sobel算子 sobel算子对图像求一阶导数。一阶导数越大,说明像素在该方向的变化越大,边缘信号越…

python链接池和pymysql批量入库——从0实现大规模异步爬虫框架项目4

我将这个链接池和批量入库封装了一个工具类上传了pypi,可以直接import使用 使用也较为简单&#xff0c;导入PooledDBhelper的DBhelper&#xff0c;调用DBhelper.PooledDBhelper()方法传入数据库链接信息创建一个链接池即可 pip install PooledDBhelper1.0.0 -----------------…

虚析构函数的作用

类的析构函数是为了释放内存资源&#xff0c;析构函数不被调用的话就会造成内存泄漏。虚析构函数定义为虚析构函数是为了当用一个基类的指针删除一个派生类的对象时&#xff0c;派生类的析构函数会被调用。但并不是要把所有类的析构函数都写成虚函数。只有当一个类被用来作为基…

信息论复习—卷积码

目录 卷积码的基本概念&#xff1a; 卷积码与分组码的不同特点&#xff1a; 卷积码的构造与表示方法&#xff1a; 卷积码编码器的结构&#xff1a; 卷积码(3,1,3): 卷积码的卷积关系: 卷积码的生成矩阵: 卷积码的多项式: 系统码结构的卷积码: 卷积码的监督矩阵: 卷积…

Pipenv使用指南:轻量级虚拟环境管理工具详解

前言 终于能够挤出一点时间来总结最近学到的一些技术知识点了&#xff0c;博主这两周被居家隔离-集中隔离-居家隔离来回折腾&#xff0c;现在终于是得到解放能够空出的时间来写写博客了&#xff0c;但是项目又催的紧&#xff0c;写博文的时间还是有限&#xff0c;这周我会尽量…

正则语言的性质

正则语言的性质 一、正则语言的性质 1.正则语言的泵引理 设LLL是正则语言&#xff0c;则存在与LLL相关的常数nnn满足&#xff1a;对于任何LLL中的串www&#xff0c;如果∣w∣≥n|w|\geq n∣w∣≥n&#xff0c;则我们就能把www打断为三个串wxyzwxyzwxyz使得&#xff1a; y̸ϵ…

2011年专业408

文章目录0 结果1 题目2 思路2.1 思路1&#xff08;暴力解&#xff1a;排序&#xff09;2.2 思路2&#xff08;较优解&#xff1a;归并合并数组&#xff09;2.3 思路3&#xff08;较优解&#xff1a;数组指针后移&#xff09;2.4 思路4&#xff08;最优解&#xff1a;两个数组的…

ARM BTI指令介绍

目录 一、JOP 二、BTI 三、启用BTI 四、BTI是怎么实现的 一、JOP JOP&#xff08;Jump-oriented programming&#xff09;类似于ROP&#xff08;Return-Oriented Programming&#xff09;。在 ROP 攻击中&#xff0c;会扫描出useful gadgets&#xff08;易被攻击的一段代码…

【数据结构】顺序队列的原理及实现

1.什么是队列 队列是一种比较特殊的线性表&#xff0c;特殊就在于它只允许在表的前端来进行删除&#xff0c;在表的后端来进行插入&#xff0c;队列它是一种操作受限制的线性表。插入的一端称为队尾&#xff0c;删除的一端称为队头&#xff0c;队列里没有元素就称它为空队列。…

快速使用代码编辑工具vim+ctags+cscope快捷使用itop3568开发板

当以上配置全部完成后&#xff0c;每当拿到新的工程代码&#xff0c;进入相关代码目录&#xff0c;利用 vim ./命令打 开当前目录&#xff0c; 然后 crtl 生成插件所需文件&#xff0c;最后使用命令:qa!退出 vim。此步只需进行一 次。 在此目录中打开任意代码文件或任意子目录…

jdk8新特性-日期时间

1、介绍 日期时间类在Java开发中是必不可少的&#xff0c;前后端如何传递时间参数、数据库的时间在Java中对应什么类型、Java中时间转换的各种方式有哪些&#xff1f; 2、Date类 Date类是JDK1.0时期推出来的第一代时间类&#xff0c;位于java.util包下&#xff0c;是最常用的…