0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

C语言指针

嵌入式技术 来源:嵌入式技术 作者:嵌入式技术 2022-08-18 17:36 次阅读

C语言指针

1、指针定义

  指针是一个变量, 它保存的是另一个变量的地址, 即内存位置的直接地址。

int ptr; //整型变量,ptr+1 表示变量值+1;
const int ptr;//只读变量,和int const ptr效果一致;
int *ptr1; //定义一个整型指针, ptr+1 表示地址偏移 int 类型字节;
int ptr[3];//3 个成员的整型数组, ptr+1 表示指向 ptr[1]的地址;
int *ptr[3];//指针数组,ptr[3]是数组,int*再与 ptr[3]结合成指针数组, 表明数组中保存着 int 类型的指针, ptr+1 表示指向 ptr[1][]的地址, 即二维数组 ptr[1][0]的地址;
int (*ptr)[3];//数组指针,()优先级高,(*ptr)是指针, 再与[3]结合, 说明指针所指向的内容是数组, 最后和 int 结合, 表示数组元素类型是 int 类型。ptr+1 表示指向 ptr[1][]的地址, 即 ptr[1][]的地址;
int **ptr;//二维指针变量, 保存一维指针变量的地址;
int const *ptr;//常量指针,ptr指向的内容不可以修改,但可以改变指向;
int *const ptr;//指针常量,ptr的指向不可以修改,但可以修改指向的内容;

2、*p++、 *(p++)、 *++p、 ++*p、 *p+1、 *(p+1)

#include 
int main()
{
	int buff[]={10,20,30};
	int *p=buff;
	/*1 buff[0]的地址:&buff[0]*/
	printf("print1 buff addr:%#x\n",buff);
	/*2 buff[0]的地址:&buff[0]*/
	printf("print2 p addr:%#x\n",p);
	/*3 偏移 sizeof(int)字节*/
	printf("print3 p+1 addr:%#x\n",p+1);
	/*4 取 buff[0]的值*/
	printf("print4 *p=%d\n",*p);
	/*5 取 buff[0]的值+1*/
	printf("print5 *p+1=%d\n",*p+1);
	/*6 地址偏移 sizeof(int)再取值, 即 buff[1]*/
	printf("print6 *(p+1)=%d\n",*(p+1));
	/*7 先取*p 的值,再 p+1*/
	printf("print7 *p++=%d\n",*p++);
	/*8 先取*p 的值, 再(*p)+1*/
	printf("print8 ++*p=%d\n",++*p);
	/*9 先 p+1,再取*(p+1)*/
	printf("print9 *++p=%d\n",*++p);
}
  • 运行结果:
[xsw@xsw cc]$ ./a.out
print1 buff addr:0xbf98f2a0
print2 p addr:0xbf98f2a0
print3 p+1 addr:0xbf98f2a4
print4 *p=10
print5 *p+1=11
print6 *(p+1)=20
print7 *p++=10
print8 ++*p=21
print9 *++p=30

3.NULL指针和void*指针

  NULL 是标准宏定义, 用来表示空指针常量, 在声明指针变量时若没有确切地址赋值, 可以给指针变量赋NULL。

#include 
int main()
{
	char *ptr=NULL;
	printf("ptr addr:%d\n",ptr);
	return 0;
}
  • 执行结果
[xsw@xsw cc]$ ./a.out
ptr addr:0

 在大多数操作系统中程序不允许访问地址为 0 的内存, 因为该内存是操作系统保留的。 指针指向地址为 0 的内存表示该指针指向的地址不可访问。 按照惯例 NULL 指针假定为不指向任何东西。

  void 表示”无类型”, void*指针表示”无类型指针”, 即可指向任何数据类型。


#include 
int main()
{
	void *p;
	int a=100;
	char buff[]={0,10,20,30};
	p=&a;//保存 int 型变量地址
	//void*指针访取值时要保证和所指向的变量类型一致
	printf("*p=%d\n",*((int *)p));//强制转换成 int*
	p=buff;//指向字符数组首地址
	//强制转换成 char*
	printf("*p=%d\n",*(char *)p);//buff[0]
	printf("*(p+1)=%d\n",*(char *)(p+1));//地址往后偏移 char 字节: buff[1]
	printf("*p+1=%d\n",*(char *)p+1);//取出的值+1: buff[0]+1
	return 0;
}
  • 执行结果
*p=100
*p=0
*(p+1)=10
*p+1=1

  注:void 几乎只能用于指针的声明和函数返回值以及函数形参, 不能用于变量的定义。

4、二维指针

  二维指针:指向指针的指针。 保存一维指针的地址。
  指针声明:int **ptr;

#include 
int main()
{
	int a=0x12;
	int *ptr=&a;//一维指针保存变量地址
	int **pptr=&ptr;//二维指针保存一维指针本身地址
	//1 ptr==&a
	printf("line1:a addr:%#x\n",ptr);
	//2 *(&ptr)==&a
	printf("line2:*(&ptr)=%#x\n",*(&ptr));
	//3 pptr==&ptr
	printf("line3:pptr :%#x\n",pptr);
	//4 *ptr==*(&a)==a
	printf("line4:*ptr=%#x\n",*ptr);
	//5 *(&ptr)==ptr==&a
	printf("line5:*pptr=%#x\n",*pptr);
	//6 **pptr==**(&ptr)==*ptr=*(&a)
	printf("line6:**pptr=%#x\n",**pptr);
	//7 ***(&pptr)==**(&ptr)==*ptr==*(&num)=0x12
	printf("line7:**pptr=%#x\n",***(&pptr));
}
  • 执行结果:
[xsw@xsw cc]$ ./a.out
line1:a addr:0xbf90384c
line2:*(&ptr)=0xbf90384c
line3:pptr :0xbf903848
line4:*ptr=0x12
line5:*pptr=0xbf90384c
line6:**pptr=0x12
line7:**pptr=0x12

5、数组指针

指针定义:int (p)[n];指向数组整体的指针。 数组指针类型:int ()[n];

()优先级高, 所以 p 是一个指针, 指向一个整型的一维数组, 一维数组的成员个数位 n, 也就是说 p 的步长为 n。 即 p+1 偏移的地址为 n 个 int 型长度。 因此数组指针也称为行指针。

优先级: () > [] > *

示例一:数组指针指向一维数组示例

#include 
int main()
{
	int buff[]={11,22,33,44,55,66};
	int (*ptr)[6];//数组指针,指向数组整体
	ptr=&buff;
	int i;
	//数组指针 ptr+1 偏移指向的数组整体大小,即偏移 6*sizeof(int)=24 字节
	printf("ptr addr:%#x\n",ptr);
	printf("(ptr+1) addr:%#x\n",ptr+1);
	/*数组指针遍历 buff*/
	for(i=0;i<6;i++)
	{
		printf("%d ",*(*ptr+i));//或*(ptr[0]+i)或 ptr[0][i]
	}
	printf("\n");
	return 0;
}
  • 执行结果:
[root@xsw cc]# ./a.out
ptr addr:0xbfbc8ce0
(ptr+1) addr:0xbfbc8cf8
11 22 33 44 55 66

示例二:数组指针指向二维数组示例:

#include 
int main()
{
	int buff[][3]={1,10,3,4,5,6};//每行有 3 个元素
	int (*p)[3]=buff;
	printf("*p[0]=%d\n",*p[0]);//等价于 buff[0][0]
	printf("*(p[0]+1)=%d\n",*(p[0]+1));//等价于 buff[0][1]
	printf("*p[1]=%d\n",*p[1]);//等价于 buff[1][0]
}

6、指针数组

  定义:int p[n];数组中保存 int指针。指针数组类型:int *[n], p的类型是 int **,p+1 偏移的地址为:sizeof(int *)。
  示例一:将一维数组赋值给指针数组:

#include 
int main()
{
	int buff[]={11,22,33,44,55,66};
	/*
	//初始化直接赋值
	int *ptr[10]={&buff[0],&buff[1],&buff[2],&buff[3],&buff[4],&buff[4]}
	*/
	int *ptr[10];//指针数组,数组中保存 int 型指针
	/*数组指针赋值*/
	int i;
	for(i=0;i<6;i++)
	{
		*(ptr+i)=&buff[i];//或:buff+i
	}
	for(i=0;i<6;i++)
	{
		printf("%d ",*(*ptr+i));
	}
	printf("\n");
	return 0;
}
  • 运行结果:
[root@xsw cc]# ./a.out
11 22 33 44 55 66

  示例二:将二维数组赋值给指针数组示例

#include 
void tow_array(int (*buff)[3],int line);
int main()
{
	int buff[][3]={1,10,3,4,5,6};//每行有 3 个元素
	int *p[3];
	*p=buff[0];
	p[0]=buff[0];
	*(p+1)=buff[1];
	printf("%d\n",(*p)[0]);//等价于:p[0][0]
	printf("%d\n",(*p)[1]);//等价于 p[0][1]
	printf("%d\n",*(p[0]+1));//等价于 p[0][1]printf("%d\n",*(p+1)[0]);//等价于 p[1][0], *(p+1)指向 buff[1][0]地址
	printf("%d\n",*(*(p+1)+1));//等价于 p[1][1]
}
printf("%d\n",*(p+1)[0]);//等价于 p[1][0], *(p+1)指向 buff[1][0]地址
printf("%d\n",*(*(p+1)+1));//等价于 p[1][1]

  注:二维数组赋值给指针数组时 p=buff 是错误的。

7、函数指针

  函数指针:指向函数的指针变量。 本质是指针变量。

#include 
int func(int a,int b);
int main()
{
	//pfunc 表示函数指针变量
	int (*pfunc)(int ,int );//定义函数指针,可以在定义时初始化
	pfunc=func;//初始化函数指针,也可写成 pfunc=&func
	int data=pfunc(10,20);
	printf("%d\n",data);
}
int func(int a,int b)
{
	return a+b;
}

8、回调函数

#include 
int func_1(int a,int b);
int func_2(int a,int b);
int func_3(int a,int b);
void func_Callback(int a,int b,int (*pfunc[])(int,int),int num);
int main()
{
	int data;
	int i=0;
	//定义函数指针数组
	int (*pfunc[3])(int ,int)={func_1,func_2,func_3};
	func_Callback(30,20,pfunc,sizeof(pfunc)/sizeof(int *));
}
int func_1(int a,int b)
{
	printf("\t[%s] %s line:%d %d+%d=%d\n",__FILE__,
										__FUNCTION__,
										__LINE__,
										a,b,a+b
										);
	return a+b;
}
int func_2(int a,int b)
{
	printf("\t[%s] %s line:%d %d*%d=%d\n",__FILE__,
											__FUNCTION__,
											__LINE__,
											a,b,a*b
											);
	return a*b;
}
int func_3(int a,int b)
{
	printf("\t[%s] %s line:%d %d%%%d=%d\n",__FILE__,
											__FUNCTION__,
											__LINE__,
											a,b,a%b
											);
	return a%b;
}
/***************************回调函数******************
**
**
**形参:int a,int b ---函数指针所需要动形参
** int (*pfunc[])(int,int) --- 函数指针数组
** int num ---函数指针数组成员个数
**
*********************************************************/
void func_Callback(int a,int b,int (*pfunc[])(int,int),int num)
{
	int i;
	int data;
	for(i=0;i
  • 运行结果:

[xsw@xsw cc]$ ./a.out
[func.c] func_1 line:17 30+20=50
data=50
[func.c] func_2 line:22 30*20=600
data=600
[func.c] func_3 line:27 30%20=10
data=10

审核编辑:汤梓红

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • C语言
    +关注

    关注

    180

    文章

    7527

    浏览量

    128250
  • 指针
    +关注

    关注

    1

    文章

    473

    浏览量

    70361
收藏 人收藏

    评论

    相关推荐

    不错的C语言指针教程.pdf

    不错的C语言指针教程.pdf
    发表于 08-11 00:28

    C语言指针详解

    ];//指针的类型是 int(*)[3] (5)int*(*ptr)[4];//指针的类型是int*(*)[4] 怎么样?找出指针的类型的方法是不是很简单? 完整的C
    发表于 07-04 03:34

    C语言指针的高级用法

    C语言指针搞不好说实话实在是太麻烦的一个东西,而且C语言指针还是绕不过的一个坎,所以我觉得还是苦
    发表于 11-06 16:50

    一文知道PHP`引用`和C语言`指针`的区别?

    PHP`引用`和C语言`指针`的区别是什么
    发表于 10-27 08:27

    什么是C语言指针变量

    C语言指针变量
    发表于 12-15 07:22

    C语言指针在32位单片机上有哪些应用呢

    C语言指针有哪些应用呢?C语言指针在32位单片机上有哪些应用呢?
    发表于 02-25 07:37

    C语言指针赋值有何作用

    C语言指针赋值有何作用?给普通变量的赋值与给指针变量的赋值有何不同?
    发表于 02-25 06:10

    单片机C语言指针有什么用处呢?

    单片机C语言指针有什么用处呢
    发表于 10-23 07:18

    C语言指针电子教程

    本资料是一份不错的关于C语言指针的电子教程,希望对大家有所帮助... 指针简介 指针是C语言中广泛使用的一种数据类型。 运用
    发表于 07-30 16:00 77次下载

    C语言_指针总结_经典讲解

    C语言_指针总结_经典讲解。
    发表于 01-06 13:47 10次下载

    C语言指针函数和函数指针详细介绍

    C语言指针函数和函数指针详细介绍。。。。。。。
    发表于 03-04 15:27 5次下载

    C语言指针跨函数访问

    C语言指针跨函数访问
    发表于 12-16 17:23 1次下载

    嵌入式开发之C语言指针

    学习 C 语言指针既简单又有趣。通过指针,可以简化一些 C 编程任务的执行。
    的头像 发表于 11-06 17:09 2908次阅读
    嵌入式开发之C<b class='flag-5'>语言</b>的<b class='flag-5'>指针</b>

    一文讲通C语言指针资料下载

    电子发烧友网为你提供一文讲通C语言指针资料下载的电子资料下载,更有其他相关的电路图、源代码、课件教程、中文资料、英文资料、参考设计、用户指南、解决方案等资料,希望可以帮助到广大的电子工程师们。
    发表于 04-24 08:44 10次下载
    一文讲通C<b class='flag-5'>语言</b><b class='flag-5'>指针</b>资料下载

    【C语言进阶】C语言指针的高阶用法

    【C语言进阶】C语言指针的高阶用法
    的头像 发表于 08-31 13:24 1948次阅读