拿捏指针(一)---对指针的基本认识(初级)

这篇具有很好参考价值的文章主要介绍了拿捏指针(一)---对指针的基本认识(初级)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

点击此处,了解对指针的进阶认识(中级)

点击此处,了解对指针的高级认识(高级)

指针是什么?

指针的定义

在计算机科学中,指针(Pointer)是编程语言中的一个对象,利用地址,它的值直接指向(points to)存在电脑存储器中另一个地方的值。由于通过地址能找到所需的内存单元,可以说地址指向该内存单元。因此,将地址形象化的称为“指针”。意思是通过它能找到以它为地址的内存单元。

这是官方对指针的定义,其实我们可以理解为:在内存中,内存被细分为一个个大小为一个字节的内存单元,每一个内存单元都有自己对应的地址。

拿捏指针(一)---对指针的基本认识(初级)

我们可以将这些内存单元形象地看成一个个的房间,将内存单元(房间)对应的地址形象地看成房间的门牌号。而我们通过门牌号(地址)就可以唯一的找到其对应的房间(内存单元),即地址指向对应内存单元。所以说,可以将地址形象化的称为“指针”

指针变量是用于存放地址的变量。(存放在指针中的值都将被当作地址处理)

#include<stdio.h>
int main()
{
	int a = 10;//在内存中开辟一块空间
	int* p = &a;//将a的地址取出,放到指针变量p中
	return 0;
}

总结:

指针变量是用于存放地址的变量。(存放在指针中的值都将被当作地址处理)

指针的大小

对于32位的机器,即有32根地址线,因为每根地址线能产生正电(1)或负电(0),所以在32位的机器上能够产生的地址信号就是32个0/1组成的二进制序列:

拿捏指针(一)---对指针的基本认识(初级)

一共 2^32 个地址。
同样的算法,在64位的机器上一共能产生 2^64 个不同的地址。
2^32 可以用32个bit位进行存储,而8个bit位等价于1个字节,所以在32位的平台下指针的大小为4个字节。
2^64 可以用64个bit位进行存储,所以在64位的平台下指针的大小为8个字节。

总结:

在32位平台下指针的大小为4个字节,在64位平台下指针的大小为8个字节。

指针类型

指针有哪些类型?

我们知道,变量的类型有int,float,char等。那么指针有没有类型呢?回答是肯定的。

指针的定义方式是type+ *

char * 类型的指针存放的是char类型的变量地址;
int * 类型的指针存放的是int类型的变量地址;
float * 类型的指针存放的是float类型的变量地址等。

指针不同类型有什么意义?

1.指针±整数

若指针类型为int * 的指针+1,那么它将跳过4个字节的大小指向4个字节以后的内容:

拿捏指针(一)---对指针的基本认识(初级)

若指针类型为char * 的指针+1,那么它只会跳过1个字节的大小指向下一个字节的内容,以此类推。

2.指针解引用

指针的类型决定了指针解引用的时候能够访问几个字节的内容。
若指针类型为int *,那么将它进行解引用操作,它将可以访问从指向位置开始向后4个字节的内容:

拿捏指针(一)---对指针的基本认识(初级)

若指针类型为char *,那么将它进行解引用操作,它将可以访问从指向位置开始向后1个字节的内容,以此类推。

总结:

指针的类型决定了指针向前或向后走一步有多大距离。
指针的类型决定了指针在进行解引用操作时,能向后访问的空间大小。

野指针

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

野指针的成因

1.指针未初始化

#include<stdio.h>
int main()
{
	int* p;
	*p = 10;
	return 0;
}

局部指针变量p未初始化,默认为随机值,所以这个时候的p就是野指针。

2.指针越界访问

#include<stdio.h>
int main()
{
	int arr[10] = { 0 };
	int* p = &arr[0];
	int i = 0;
	for (i = 0; i < 11; i++)
	{
		*p++ = i;
	}
	return 0;
}

当指针指向的范围超出arr数组时,p就是野指针。

3.指针指向的空间被释放

#include<stdio.h>
int* test()
{
	int a = 10;
	return &a;
}
int main()
{
	int* p = test();
	return 0;
}

指针变量p得到地址后,地址指向的空间已经释放了,所以这个时候的p就是野指针。(局部变量出了自己的作用域就被释放了)

如何避免野指针?

1.指针初始化
当指针明确知道要存放某一变量地址时,在创建指针变量时就存放该变量地址。
当不知道指针将要用于存放哪一变量地址时,在创建指针变量时应置为空指针(NULL)。

#include<stdio.h>
int main()
{
	int a = 10;
	int* p1 = &a;//明确知道存放某一地址
	int* p2 = NULL;//不知道存放哪一地址时置为空指针
	return 0;
}

2.小心指针越界

3.指针指向的空间被释放后及时置为NULL

4.使用指针之前检查有效性
在使用指针之前需确保其不是空指针,因为空指针指向的空间是无法访问的。

指针运算

指针 ± 整数

#include<stdio.h>
int main()
{
	int arr[5] = { 0 };
	int* p = arr;
	int i = 0;
	for (i = 0; i < 5; i++)
	{
		*(p + i) = i;
	}
	return 0;
}

指针 - 指针

指针-指针的绝对值是是两个指针之间的元素个数。

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

指针的关系运算

指针的关系运算,即指针之间的大小比较。
我们如果要将一个数组中的元素全部置0,可以有两种方法。

第一种:从前向后置0

#include<stdio.h>
int main()
{
	int arr[5] = { 1, 2, 3, 4, 5 };
	int* p = &arr[0];
	for (p = &arr[0]; p <= &arr[4]; p++)
	{
		*p = 0;
	}
	return 0;
}

最终指向数组最后一个元素后面的那个内存位置的指针将与&arr[4]比较,不满足条件,于是结束循环。

第二种:从后向前置0

#include<stdio.h>
int main()
{
	int arr[5] = { 1, 2, 3, 4, 5 };
	int* p = &arr[4];
	for (p = &arr[4]; p >= &arr[0]; p--)
	{
		*p = 0;
	}
	return 0;
}

最终指向第一个元素之前的那个内存位置的指针将与&arr[0]比较,不满足条件,于是结束循环。

这两种方法在绝大部分编译器下均能将arr数组中的元素置0,但是我们要尽量使用第一种方法,因为标准并不保证第二种方法可行。

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

二级指针

我们知道,指针变量是用于存放地址的变量。但是指针变量也是变量,是变量就有地址,那么存放指针变量的地址的变量是什么呢?

其实,存放普通变量的地址的指针叫一级指针,存放一级指针变量的地址的指针叫二级指针,存放二级指针变量地址的指针叫三级指针,以此类推。

#include<stdio.h>
int main()
{
	int a = 10;
	int* p1 = &a;
	int** p2 = &p1;
	return 0;
}

在这里,我们用一级指针p1存放了普通常量a的地址,用二级指针p2存放了一级指针p1的地址。

这时如果我们要得到a的值,就有两种方法

方法一:对一级指针p1进行一次解引用操作即可得到a的值,即*p1。

方法二:对二级指针p2进行一次解引用操作即可得到p1的值,而p1的值就是a的地址,所以再对p2进行一次解引用操作即可得到a的值,也就是对二级指针p2进行两次解引用操作即可得到a的值,即**p2。文章来源地址https://www.toymoban.com/news/detail-486167.html

到了这里,关于拿捏指针(一)---对指针的基本认识(初级)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • BDA初级分析——认识SQL,认识基础语法

    SQL作为实用技能,热度高、应用广泛  在对数据分析人员的调查中SQL长期作为热度排名第-一的编程语言超过Python和R SQL:易学易用,高效强大的语言 SQL: Structured Query Language 结构化查询语言 SQL:易学易用,类似英文语法类的语言结构  SQL:标准语句,写法成熟,应用广泛 SQ

    2024年02月12日
    浏览(29)
  • 前端学习C语言 - 初级指针

    本篇主要介绍: 指针和变量的关系 、指针类型、 指针的运算符 、空指针和野指针、 指针和数组 、 指针和字符串 、const 和指针、以及 gdb 调试段错误 。 指针是一种特殊的变量。存放地址的变量就是指针。 int num = 1; 会申请4个字节的内存来存放数字1,每次访问 num 就是访问

    2024年02月10日
    浏览(42)
  • 【C生万物】 指针篇 (初级)

     欢迎来到 Claffic 的博客  💞💞💞                               👉  专栏: 《C生万物 | 先来学C》👈 前言: 面对C语言,很多童鞋都会高呼:指针难,指针难,对于我来说,指针是解决问题的一大杀器,是C/C++的 灵魂 ,先不考虑难不难的问题,上了车再说。   目录

    2024年02月02日
    浏览(44)
  • 认识C++指针

    目录 前言: 1.指针未初始化的危险性 2.指针与十六进制数字 3.使用new分配内存空间 4.使用delete释放内存 5.使用new来创建动态数组  6.使用动态数组 7.指针运算   期待已久的指针篇来啦,这篇全都是有关指针的知识, 喜欢指针的读者可以大饱眼福^ ^ 。 关于指针的声明和初始化

    2024年02月02日
    浏览(24)
  • 【C语言】——认识指针变量和地址,以及指针变量类型的意义

    🎥 岁月失语唯石能言的个人主页         🔥 个人栏专: 秒懂C语言 ⭐ 若在许我少年时,一两黄金一两风      目录 前言 一、指针变量和地址 1.1 取地址操作符() 1.2 指针变量和解引用操作符(*) 1.2.1 指针变量 1.2.2 如何拆解指针类型 1.2.3 解引用操作符 1.3 指针变量

    2024年02月04日
    浏览(54)
  • 【开卷数据结构 】指针的初步认识

    说到指针,想必大家都不陌生,指针的最大特点就是难以理解,它是编程中很基础也是很重要的概念,指针可以有效的实现像树,链表这类高级的数据结构。 在了解指针是什么之前,我们需要先了解什么是计算机的内存,什么是地址。 内存: 计算机内存大部分时候指的是随

    2023年04月16日
    浏览(41)
  • C++:类和对象(上)---初步认识类和this指针

    C语言是一门面向过程的语言关注的是过程,确认一个问题求解的步骤,再一步一步对它进行解决 C++是一门基于面向对象的语言,它更关注的是对象,将一个事情分成不同的对象,再用对象完成问题的解决 在C语言中有结构体,但结构体中只能定义变量,而在C++中还可以定义函

    2024年02月16日
    浏览(33)
  • C语言第十三课--------初阶指针的认识--------重要部分

    🎂        ✨✨✨✨✨✨🍧🍧🍧🍧🍧🍧🍧🎂    🎂      作者介绍:                              🎂🎂        🎂 🎉🎉🎉🎉🎉🎉🎉              🎂           🎂作者id:老秦包你会,         🎂 简单介绍:🎂🎂🎂🎂🎂🎂🎂🎂🎂🎂🎂🎂🎂🎂🎂

    2024年02月13日
    浏览(39)
  • 快慢指针该如何操作?本文带你认识快慢指针常见的三种用法及在链表中的实战

    很多同学都听过 快慢指针 这个名词,认为它不就是定义两个引用(指针)一前一后吗?是的,它的奥秘很深,它的作用究竟有哪些?究竟可以用来做哪些题目?下面我将一一带你了解和应用 下面的本节的大概内容,有疑惑的点,欢迎小伙伴们留言 目录 1.简述快慢指针 2.快慢

    2024年02月04日
    浏览(34)
  • 【是C++,不是C艹】 类与对象 | 认识面向对象 | 访问限定符 | 封装 | this指针

    💞💞 欢迎来到 Claffic 的博客 💞💞  👉  专栏: 《是C++,不是C艹》👈 前言: 在C++入门之后,就要进入C++的第一个核心:类与对象,这期带大家认识认识面向对象编程,访问限定符,封装以及 this 指针。 注: 你最好是学完了C语言,并学过一些初阶的数据结构。 (没有目

    2024年02月07日
    浏览(44)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包