c语言的灵魂——指针

大家都认为,c语言之所以强大,以及其自由性,很大部分体现在其灵活的指针运用上。因此,说指针是c语言的灵魂,一点都不为过。那么加强对指针的认识和理解,是提高C语言水平很关键的一部分。下面是一些指针总结,希望能够抛砖引玉大家相互交流相互学习。
1. 指针是什么? 
指针,是一个无符号整数(unsigned int),它是一个以当前系统寻址范围为取值范围的整数。32位系统下寻址能力(地址空间)是4G-byte(0~2^32-1)二进制表示长度为32bit(也就是4B)。
所以我们经常看到这样的面试题
定义如下数据类型:
char * p;
Int * p;
struct stu{
Int m;
char a[10];
char * s;
……
};
Struct stu *p;
问:sizeof p是多少?
由于以上的p全是指针类型的变量所以在同一操作系统下他的大小是一致的,对于一个32为的系统来说其值为4.
2. 指针能干什么?
要说明白这个问题首先就要说说内存地址,计算机中的内存都是编址的,就像我们住所的地址一样。在程序编译或者运行的时候,系统(可以不关心具体是什么,可能是编译器,也可能是操作系统)开辟了一张表。每遇到一次声明语句(包括函数的传入参数的声明)都会开辟一个内存空间,并在表中增加一行纪录。记载着一些对应关系。如下表所示:
指针则是一个用来指示一个内存地址的计算机语言的变量或中央处理器(CPU)中寄存器(Register)。指针变量通过存储其他量的地址值来建立指示关系。正是由于这一点所以指针是一个与操作系统寻址范围相关的无符号整数。
指针一般出现在比较近机器语言的语言,如汇编语言或C语言。面向对象的语言如Java一般避免用指针。指针一般指向一个函数或一个变量。在使用一个指针时,一个程序既可以直接使用这个指针所储存的内存地址,又可以使用这个地址里储存的变量或函数的值。指针可以用来有效地表示复杂的数据结构,可以用于函数参数传递并达到更加灵活使用函数的目的.使C语言程序的设计具有灵活、实用、高效的特点。
3. 指针怎么用?
指针的使用大致分为如下的几个形式:
(1) 普通指针:指向整形、字符型、自定义结构等的常见指针。
声明格式:类型 * 变量名
例 如:
char * p; 表示指向一个char型数据变量的指针p。
struct stu *s;表示指向一个stu型结构体的指针p。
赋 值:可以在声明变量的时候赋值,也可以在声明之后赋值。
如:定义 int a;
int * p=&a;
或者,定义 int a;
int *p;
p=&a;都是可以的
(2) 数组指针:指向数组的指针。
声明格式:类型 (*变量名)[个数]
例 如:
char (*p)[10] 表示指向一个有十个元素的char型数组的指针。
赋 值:可以再变量声明的时候赋值,也可以声明之后赋值
如:定义 int a[10];
int (*p)[10]=&a;
(3) 多级指针:指向指针的指针。
声明格式:类型 *… * 变量名
例 如:
char **p;表示一个指向char型数据指针的指针p。
赋 值:
如:定义 char a;
char *p=&a;
char **p=&p;
(4) 函数指针:指向函数的指针。
声明格式:类型 (*p)(参数)
例 如:
int (*p)(char a); 表示指向一个返回值为int型,有一个char型参数的函数的指针。
赋 值:
如:定义 int fun(char *s,int a);
Int (*p)(char *s,int a);
P=fun;
(5) 指针数组:数组元素是指针的数组,注意变量的本质是数组不过其中的元 素是指针。
声明格式:类型 *变量名[个数]
例 如:
int *p[10]; 表示一个有10个以指向整形数据的指针为元素的数组。
赋 值:
如:定义 int s;
int *p[1];
p[0]=&s;
(6) 指针函数:返回值是指针的函数,注意本质是函数只是返回值是指针。
声明格式:类型 *函数名(参数)
例 如:
int *p(char m);表示一个有一个字符型参数返回只需向整形变量指针的函数。
赋 值:
如:定义
char *fun(); 
4. 指针分析
记得看过一些关于指针的资料,作者是这样总结指针的,我觉得分析的很精辟,在这里和大家分享一下:
要搞清一个指针需要搞清指针的四方面的内容:指针的类型、指针所指向的类型、指针的值或者叫指针所指向的内存区、指针本身所占据的内存区。
(1)指针的类型
从语法的角度看,你只要把指针声明语句里的指针名字去掉,剩下的部分就是这个指针的类型。这是指针本身所具有的类型。让我们看看例一中各个指针的类型:
【1】int*ptr;//指针的类型是int*

【2】char*ptr;//指针的类型是char*

【3】int**ptr;//指针的类型是int**

【4】int(*ptr)[3];//指针的类型是int(*)[3]

【5】int*(*ptr)[4];//指针的类型是int*(*)[4]

(2)指针所指向的类型
当你通过指针来访问指针所指向的内存区时,指针所指向的类型决定了编译器将把那片内存区里的内容当做什么来看待。从语法上看,你只须把指针声明语句中的指针名字和名字左边的指针声明符*去掉,剩下的就是指针所指向的类型。例如:

【1】int*ptr; //指针所指向的类型是int

【2】char*ptr; //指针所指向的的类型是char

【3】int**ptr; //指针所指向的的类型是int*

【4】int(*ptr)[3]; //指针所指向的的类型是int()[3]

【5】int*(*ptr)[4]; //指针所指向的的类型是int*()[4]

在指针的算术运算中,指针所指向的类型有很大的作用。指针的类型(即指针本身的类型)和指针所指向的类型是两个概念。当你对C 越来越熟悉时,你会发现,把与指针搅和在一起的"类型"这个概念分成"指针的类型"和"指针所指向的类型"两个概念,是精通指针的关键点之一。
(3)指针的值
或者叫指针所指向的内存区或地址指针的值是指针本身存储的数值,这个值将被编译器当作一个地址,而不是一个一般的数值。在32 位程序里,所有类型的指针的值都是一个32 位整数,因为32 位程序里内存地址全都是32 位长。指针所指向的内存区就是从指针的值所代表的那个内存地址开始,长度为si zeof(指针所指向的类型)的一片内存区。以后,我们说一个指针的值是XX,就相当于说该指针指向了以XX 为首地址的一片内存区域;我们说一个指针指向了某块内存区域,就相当于说该指针的值是这块内存区域的首地址。指针所指向的内存区和指针所指向的类型是两个完全不同的概念。以后,每遇到一个指针,都应该问问:这个指针的类型是什么?指针指的类型是什么?该指针指向了哪里?(重点注意)
(4)指针本身所占据的内存区
指针本身占了多大的内存?你只要用函数sizeof(指针的类型)测一下就知道了。在32 位平台里,指针本身占据了4 个字节的长度。指针本身占据的内存这个概念在判断一个指针表达式(后面会解释)是否是左值时很有用。
5. &和*
&和*是和指针和地址相关的两个符号,使用它们时可能会有两种含义在不同的场合含义不同。
(1) 当用于声明一个变量时:
*表示:声明的该整数指向某个内存地址,一次访问sizeof(type)长度。
&表示:在C++程序声明变量的时候的&,只是表明该声明的变量是一个引用,这个引用声明时不开辟新空间,它在内存分配表加入新的一行,该行内存地址等于和调用时传入的对应参数内存地址。
(2) 当用于操作一个变量时:
*表示:这样一种操作,该操作返回以他后面变量值为地址的内存空间存储的值。
&表示:这样一种操作,该操作的返回值是他后面的变量在声明时分配给该变量的地址空间。
举例:
int * p; 这里的*表示声明的变量是一个指针型变量。
*p=5; 这里的*表示以该变量值为地址所表示的内存空间存储的值为5;
int &p; 这里的&表示声明的变量p为一个引用变量。
int *p=&a; 这里的&表示对变量a进行取址操作,将地址付给p。
6. 容易混淆的指针相关概念
(1) 指针数组和数组指针
如果细心的话,这两者之间是很好区分的。指针数组的本质是数组,数组指针的本质是指针这一点可以从优先级进行判断。
例如:
  int *p[3]; 首先从P 处开始,先与[]结合,因为其优先级比*高,所以P 是一个数组,然后再与*结合,说明数组里的元素是指针类型,然后再与int 结合,说明指针所指向的内容的类型是整型的,所以P 是一个由返回整型数据的指针所组成的数组
int (*p)[3]; 首先从P 处开始,先与*结合,说明P 是一个指针然后再与[]结合(与"()"这步可以忽略,只是为了改变优先级),说明指针所指向的内容是一个数组,然后再与int 结合,说明数组里的元素是整型的.所以P 是一个指向由整型数据组成的数组的指针
(2) 指针函数和函数指针
指针函数和函数指针的区分方法和数组指针与指针数组的区分方法一致利用优先级很容易进行区分。
int (*p)(int); 从P 处开始,先与指针结合,说明P 是一个指针,然后与()结合,说明指针指向的是一个函数,然后再与()里的int 结合,说明函数有一个int 型的参数,再与最外层的int 结合,说明函数的返回类型是整型,所以P 是一个指向有一个整型参数且返回类型为整型的函数的指针
int *p(int); 从P 开始,先与()结合,说明P 是一个函数,然后进入()里面,与int 结合,说明函数有一个整型变量参数,然后再与外面的*结合,说明函数返回的是一个指针.所以P 是一个参数为一个整数据且返回一个指向整型数据的指针的函数.
以上就是我对C语言指针的认识,我想要想学好C语言不能只顾理论,理论源于实践在实践中摸索总结理论知识我想会更有效也会有更多新的收获。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值