【C语言初阶】赶紧来,指针详细讲解

1.什么是指针

指针是什么 ?理解指针的两个要素
1.指针是内存中一个最小单元的编号,也就是地址
2.平时口语中说的指针,通常指的是指针变量,是用来存放内存地址的变量

所以指针就是地址,我们口头说的指针通常指的是指针变量。

1.1图解+分析指针内存中的存储

我们了解指针之前我们要先去了解内存,指针在内存中是如何存储的
在这里插入图片描述
总结:指针变量,用来存放地址的变量。(存放在指针中的值都被当成地址处理。

1.2指针大小

代码演示
在这里插入图片描述

总结:
指针变量是用来存放地址的,地址是唯一标示一个内存单元的。
指针的大小在32位平台是4个字节,在64位平台是8个字节

2.指针和指针类型

我们都知道,变量有不同的类型,整形,浮点型等。那指针有没有类型呢?当然有。

char *pc = NULL;
int *pi = NULL;
short *ps = NULL;
long *pl = NULL;
float *pf = NULL;
double *pd = NULL;

指针定义方式: 类型 + *
char* 类型的指针是为了存放 char 类型变量的地址。
short* 类型的指针是为了存放 short 类型变量的地址。
int* 类型的指针是为了存放 int 类型变量的地址。

在这里插入图片描述

2.1指针 + - 整数的意义

在这里插入图片描述

总结:
指针类型决定了指针的步长(向前向后走一步多大距离)
int* 指针+1,意思是跳过一个整形,也就是向后走四个字节
char* 指针+1,意思是跳过一个字符,也就是向后走一个字节
double指针+1,意思是跳过一个double,也就是向后走八个字节
short
向后走两个字节,
long向后走四个字节
long long
向后走八个字节
这里可以加减任何整数,看你使用的需求。

3.野指针

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

3.1野指针的成因

1.指针未初始化

#include <stdio.h>
int main()
{
int *p;//局部变量指针未初始化,默认为随机值,所以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 <= 10; i++)
	{
		//当指针指向的范围超出数组arr的范围时,p就是野指针
		*p = i;
		p++;
	}
	return 0;
}

3.指针指向的空间释放

#include<stdio.h>

int* test()
{
	int num = 100;
	return &num;
}
int main()
{
	int* p = test();
	*p = 200;
	return 0;
}

图解:
在这里插入图片描述

3.2如何规避指针

1.注意指针初始化
2.注意指针越界
3.指针指向空间被释放是,及时置NUML(空指针)
4.避免返回局部变量的地址
5.指针使用之前检查有效性

4.指针运算

4.1指针±整数

我们所谓的加减整数,就是-1,+1或者-2,+2等。下面我们有一段代码来解释。
在这里插入图片描述

4.2指针-指针

说到这里,可能就有疑问了,为啥没有指针+指针呢?就好比日期-日期=天数,但是日期+日期等于什么呢,其实这样是没有意义的。指针-指针本质上就是地址-地址
下面我们用代码来解释指针-指针的含义。
在这里插入图片描述

//用指针-指针来模拟实现strlen
#include<stdio.h>
int my_strlen(char* str)
{
	char* ch = str;
	while (*str)
		str++;
	return str - ch;//指针-指针
}
int main()
{
	char arr[] = "abcdef";
	int len = my_strlen(arr);
	printf("%d\n", len);
	return 0;
}

4.3指针的关系运算

在这里插入图片描述

5.指针和数组

在这里插入图片描述

数组和指针不是一个东西
数组是能够存放一组数,连续的空间,数组的大小取决于元素的个数
它们之间的联系是:
数组名是地址(指针)
数组把首元素地址,存放在一个指针变量后,可以通过指针来访问。

6.二级指针

在这里插入图片描述

对于二级指针的运算有:
*pp 通过对pp中的地址进行解引用,这样找到的是 p , *pp其实访问的就是 p
int b = 20;
**pp = &b; 等价于 *p= &b;

**pp 先通过 *pp 找到 p ,然后对 p 进行解引用操作: *p ,那找到的是 a
**pp = 30;
等价于*pa = 30;
等价于a = 30;

7.指针数组

指针数组是数,是存放指针的数组。

7.1指针数组的定义

#include<stdio.h>
int main()
{
	int arr[10];
	//存放整形的数组
	char arr2[10];
	//存放字符的数组
	int* arr3[10];
	//存放整形指针的数组
	char* arr4[10];
	//存放字符指针的数组
	return 0;
}

7.2指针数组的用法

#include<stdio.h>
int main()
{
	int a = 1;
	int b = 2;
	int c = 3;
	int d = 4;
	int e = 5;
	int *arr[5] = { &a,&b,&c,&d,&e };//指针数组
	int i = 0;
	for (i = 0; i < 5; i++)
	{
		printf("%d ", *(arr[i]));
	}
	return 0;
}

用一维数组模拟实现一个二维数组

在这里插入图片描述

码文不易,感谢三连击
在这里插入图片描述

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值