什么是指针?
我们知道,可执行程序是由指令、数据和地址组成的。当CPU访问内存单元时,不论是读取还是写入,首先必须把内存单元的地址加载到地址总线(AB)上,同时将内存电路的“读写控制”设为有效,然后内存单元中的数据就通过数据总线(DB)“流”向了接收寄存器中,或者结果寄存器中的值“流”向了目标内存单元中。这就是一个“内存读写周期”。内存单元的地址就是指针的值。
指针是变量吗?
指针是变量,它和我们平常使用的整型变量、字符变量、浮点变量等各种变量并没有本质的差异,不同的是,他们的类型和值的含义,及解释方式。在二进制层面,指针的值就是内存单元的地址,而变量又是引用内存单元的值的别名,因此在语言层面指针的值就是变量的值。
指针的类型
C99中:指针的类型是derived from其它类型,也就是说指针的类型是由它指向的类型决定的;指针是一种reference类型,即引用类型。
简单来说就是:指针类型是一种组合类型, 类型名后面加‘*’,如int* pInt; char* pChar; long* pLong;
注意:编译器解释的时候,'*'是和其后变量名组合的,例如:int* a,b,c;只有a的指针变量,b,c都是int类型变量。
指针的值:
通过代码来探究奥秘:
#include <stdio.h>
int main()
{
int i = 100;
int *pI = &i; //声明指针变量并初始化为i的地址
int **ppI = &pI; //指针的指针
printf("Value of i :0x%x\n\n", i);
printf("Address of i :0x%x\n\n", &i);
printf("Value of pI :0x%x\n\n", pI);
printf("Address of pI :0x%x\n\n", &pI);
printf("Value of ppI :0x%x\n\n", ppI);
printf("Address of ppI :0x%x\n\n", &ppI);
}
运行结果:
解析:
我们通过&i 将i的地址赋给了指针变量pI,所以pI的值就是i的地址值。 ppI也是同理获得了pI的地址值。
注:
①全局指针变量的默认初始值为NULL。而对于非静态局部指针变量p,必须显示的指定其初始值,否则p的初始值时不可预测的(不是NULL)此时当无法用if(NULL != p)来检查p的有效性时候。所以建议,不管是全局还是局部的,静态还是非静态的,声明指针的同时初始化它,要么为NULL,要么为有效地址。
②指针的值表示某个地址,不管p为什么类型的指针,sizeof(p)永远等于4(32位平台下)。同理,在指针变量空间里面存放有符号或无符号的数,在解引用时,都当做无符号整型处理。
③只要我们始终掌握着对象的内存地址(也就是它的指针),我们就可以在任何地方对其指向的内存单元进行操作,无论是读写数据还是调用函数。这种灵活正是指针危险(可能指向无效内存对象)和不易掌握的原因。