指针(初识指针)史上最简单的认识指针

2023-11-20

本章重点

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

指针是什么?

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

其实指针就是地址。指针就是来存放地址的。

我们这样理解:

 指针

指针是个变量,存放内存单元的地址编号。(存放在指针中的值都被当成地址处理)

对应的代码如图所示。

#include<stdio.h>
int main()
{
    int a=10; //在内存中开辟一片空间
    int* p = &a; //将a的地址存放在p变量中,p就是一个指针变量
                 //p的类型是int*
    return 0;
}
  • 在32位机器上的地址是32个零或者一组成二进制序列,那地址就得用四个字节的空间来存储。所以一个指针变量的大小就应该是4个字节,
  • 那如果是64位机器上如果有64个地址线,那一个指针变量的大小就是8个字节才能存放一个地址。

总结

  • 指针是用来存放地址的,地址是唯一表示一块地址空间的指针大小
  • 指针的大小在34位平台上是4个字节,在64位平台上是8个字节。

指针和指针类型

1.指针类型决定了指针进行解引用操作的时候,能够访问空间的大小。

int* p; *p能够访问4个字节

char* p; *p能够访问1个字节

double* p; *p能够访问8个字节

2.指针类型决定了:指针走一步走多远(指针的步长)。

int* p;   p+1--->移动4个整形

char* p; p +1--->移动1个字符

double* p;p+1--->移动8个字节

 总结

指针的类型决定了指针向前或向后移动,走一步有多大(距离)

#include<stdio.h>
int main()
{

	int arr[10]={0};
    //int* p= arr;
	char* p = arr; //数组名--首元素的地址
	int i=0;
	for(i=0;i<10;i++)
	{
		*(p+i)=1;
	}
	
	return 0;
}

  • 可见代码char*只改动了10个字节为1,而int arr[10]数组是10个整型,所以没有全部改为1
  • 指针类型决定了对指针解引用的时候有多大的权限(能操作几个字节)比如char*的指针解引用就只能访问一个字节,而int*的指针的解引用就能访问四个字节

野指针

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

成因:

1.指针没有初始化

#include<stdio.h>
int main()
{

	int a;//局部变量不初始化,默认是随机值。 
	int *p;//局部的指针变量,就被初始化为随机值。 
	*p =20;
	return 0;
}

2.指针越界访问

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

 

如何避免野指针 

  • 指针初始化
int main()
{
    int b=0;
    int a=19;
    int* pa=&a;  //初始化
    int* p =NULL;  //NULL,用来初始化指针的给指针赋值
}
  • 小心指针越界
  • 指针指向空间释放,指针就置为NULL
  • 指针使用之前检查有效性。

 指针的运算

  • 指针+-整数
  • 指针-指针
  • 指针的关系运算

 指针+-整数:

#include<stdio.h>
int main()
{
	int arr[10]={1,2,3,4,5,6,7,8,9,10};//10个元素
	int i=0;
	int sz=sizeof(arr)/sizeof(arr[0]);// 元素的个数
	int* p=arr;  //数组名放首元素的地址给指针变量p
	for(i=0;i<sz;i++)
	{
		printf("%d ",*p); //打印指针指向的内容
		p=p+1;
	}
	return 0;
}

 

 

指针-指针  :得到的是指针和指针之间元素的个数

#include<stdio.h>
int main()
{
    int arr[10]={1,2,3,4,5,6,7,8,9,10};//10个元素
	printf("%d\n",&arr[9]-&arr[0]);

	return 0;
}

 

 

案例:自定义函数,用指针求字符串的长度。

//自定义函数,用指针求字符串的长度
#include<stdio.h>
int my_strlen(char* str)
{
	char* start=str;
	char* end =str;
	while(*end !='\0')
	{
		end++;
	}
	return end-start;
}

int main()
{
	char arr[]="big";
	int len = my_strlen(arr);
	printf("%d\n",len);
	return 0;
}

指针的关系运算

 

标准规定

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

如图p1可以和p2比较但是最好不要和p3比较

 指针和数组

数组可以通过指针来访问

#include<stdio.h>
int main()
{
	int arr[10]={0};
	int * p=arr;  //arr数组名代表首元素的地址,放到指针变量里面
	int i =0;
	for(i=0;i<10;i++)
	{
		*(p+i) = i; //p+i指针+整数,表示下标i元素的地址,
		             //*(p+i)解引用对下标赋值
		             //此时数组被赋值0123456789
		            //这里是指针的形式放数据
	}
	for(i=0;i<10;i++)
	{
		//printf("%d ",arr[i]);//数组的形式打印
		                     //这里相当于数组形式打印出来
		printf("%d ",*(p+i));//这里相当于指针形式打印出来

	}
	return 0;
}

printf("%d ",*(p+i));//这里相当于指针形式打印出来

printf("%d ",arr[i]);//数组的形式打印

二级指针

#include<stdio.h>
int main()
{
	int a=10;   //a是个变量
	int* pa =&a;  //a的地址放到指针变量pa里面 ,pa是个变量,具体是指针变量
	int** ppa = &pa; //ppa就是二级指针。取指针变量pa的地址,放到指针变量ppa里面
	return 0;

}

 图解:

 二级指针解引用

#include<stdio.h>
int main()
{
	int a=10;   //a是个变量
	int* pa =&a;  //a的地址放到指针变量pa里面 ,pa是个变量,具体是指针变量
	int** ppa = &pa; //ppa就是二级指针。取指针变量pa的地址,放到指针变量ppa里面
    **ppa = 30;       //*ppa解引用找到一级指针,**ppa解引用,找到a的内容
					 //改变a的内容为30
	printf("%d ",**ppa);  
	printf("%d ",a);
	return 0;

}

指针数组

指针数组指针数组是指针还是数组呢?

答案:数组,是存放指针的数组。

数组我们已经知道整型数组 ,字符数组。

#include<stdio.h>
int main()
{
	int a=10;
	int b=20;
	int c=30;
	int* arr[3]={&a,&b,&c};//指针数组,存放地址
	int i=0;
	for(i=0;i<3;i++)
	{
		printf("%d ",arr[i]);//打印数组存放的元素的地址
		printf("%d\n ",*(arr[i]));  //解引用打印数组里面具体内容
	}
	return 0;
}

 

 

 

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

指针(初识指针)史上最简单的认识指针 的相关文章

随机推荐