C语言指针初探
2013-04-29姜雪茸
姜雪茸
摘 要:本文从指针的基本概念出发,分别阐述了指针、指针变量、指针与数组、指针与函数等几个方面的基本概念。
关键词:C语言;指针;数组;函数
1 指针
理解指针首先要了解内存,掌握内存单元、内存单元的地址、内存单元的内容的基本概念。内存是由许多个大小完全一致的存储单元构成。每一个存储单元容量为一个字节。为将各存储单元区别开,给每个存储单元一个对应的编号称为存储单元的地址。而存储单元中存储的数据称为存储单元的内容。
在计算机中,所有数据都被放在内存中。如果在程序中定义了一个变量,则程序在编译过程中由系统给变量分配适当内存单元。因此,在程序中使用的变量就是内存中某个存储单元。例如,程序中定义某字符型变量i=A,编译时为其分配地址为2000的一个存储单元。则变量i被存放在地址编号为2000的单元中,此单元中存放的内容是A。地址指示出变量所在位置,即按变量地址寻找变量的值,变量的地址就称为变量的指针。通常用&表示取变量的存储地址,&i=2000。
2 指针变量
如果将变量i所在单元的地址2000作为数据存放在其他存储单元中(假设当前分配其他单元地址为3000),则变量i被存放在以地址编号为3000的存储单元的内容2000为地址的单元中。即就是存储单元3000中存放的是变量i的地址(或指针),则将存储单元3000定义为变量称为指针变量,专门用来存放变量存储地址的变量称为指针变量。通常用*表示变量的类型为指针型变量。
3 指针与数组
3.1 指针和一维数组
数组是同类型数据的有序集合。数组中的元素依次顺序的存储在一片连续的内存区域中,对数组的操作依靠数组元素的下标实现,而数组下标代表的是数组元素所在地址,地址即指针。所以用指针不但可以实现数组的操作,而且占用内存少,运行速度快。
3.2 指针和二维数组
二维数组由若干个一维数组组成。C语言将二维数组实际上定义为一个一维数组,而这个一维数组的每一个成员又是一个一维数组。假设定义int *p,a[3][4],i,j;则a数组由a[0]、a[1]、a[2]三个元素组成,而a[0]、a[1]、a[2]每个元素又分别是由4个整型元素组成的一维数组。a[0]、a[1]、a[2]依次代表二维数组每行第一个元素的地址,二维数组元素的地址可以由表达式&a[i][j]求得,或通过每行的首地址来表示。如:地址&a[0][0]可以用a[0]+0来表示,地址&a[0][1]可以用a[0]+1表示;则a[i][j]的地址可用五种方式表示:(1)&a[i][j](2)a[i]+j(3)*(a+i)+j(4)&a[0][0]+4*i+j (5)a[0]+ 4*i+j。由以上通过地址来引用二维数组元素a[i][j]对应有五种方式表达:(1)a[i][j](2)*(a[i]+j)(3)*(*(a+i)+j)(4)(*(a+i))[j](5)*(&a[0][0]+4*i+j)。
4 指针与函数
4.1 函数指针
指针可以指向整型变量、字符串、数组、也可以指向一个函数。一个函数在编译是被分配给一个入口地址。这个函数的入口地址就称为函数的指针。即用一个指针变量指向函数,然后通过该指针变量调用此函数。例如:int(*p)(int,int);表示定义了一个指向函数的指针变量p,p用来存放函数入口地址。若当前有函数int proc(int,int);则p=proc是将函数proc的入口地址赋给p,而用函数指针变量调用函数时,将(*p)代替函数名,可以表示为c=(*p)(a,b),其中a,b为实参。
函数指针变量通常是用于把指针作为参数传递到其他函数。函数的参数可以是多种类型的变量,指向函数的指针也可以作为参数实现函数地址的传递,从而实现在被调用的函数中使用实参函数。例如:某程序中函数声明为void subproc(int,int,int(*subfun)(int,int));函数调用为subproc(s,t,suba);subproc(s,t,subb);subproc(s,t,subc);其中int(*subfun)(int,int)表示subfun是指向函数的指针,它在程序中多次被调用,将函数suba,subb,subc作为实参分别传递给形参subfun。也就是将函数指针分别指向suba,subb,subc三个子函数。实现了函数的多次调用,而无需定义多个实参,增加了程序的灵活性,简化了程序。
函数指针本质是一个指针。
4.2 指针函数
指针函数本质是一个函数。
一个函数可以返回一个整型值、字符值、实型值等,也可以返回指针型的数据,即地址。例如:int *a(int x,int y);其中函数名和参数为a(int x,int y),在函数名前加上*表示此函数为指针型函数。最前面的int表示返回的指针指向整型变量。
5 指针数组与指向指针的指针
5.1 指针数组
一个数组,若其元素均为指针类型数据,称为指针数组。指针数组中的每一个元素均为指针。指针数组可以作为函数的参量使用,也常用于指向若干字符串,这样使字符串处理更加灵活方便。
5.2 指向指针的指针
一个指针变量指向其他指针类型变量,称为指向指针的指针。
例如:int i,*p1,**p2;p1=&i;p2=&p1;*p1=i;*p2=p1;则p2=&(&i);**p2=i;
一个指针变量的地址就是指向该变量的指针,也称为双重指针。例如:int **a [n]
这是一个int型指针的指针数组。a首先和[ ]结合,即a[n],表示a是一个数组,然后a[n]和其紧邻的*结合,即*a[n],表示数组a的每个元素均为指针。*a[n]再和前一个*结合(*的结合顺序为从右到左),即*(*a[n]),表示数组a的每个元素为指针,且该指针指向int型的指针,也就是说,数组a的每个元素为int型的指针的指针。
[参考文献]
[1]谭浩强.C语言程序设计(第三版)[M].清华大学出版社,2005.
[2]卫武波,陈冬.C语言指针解析[J].《软件导刊》,2012(11).