1、首先 内存和地址
大家都知道,我们可以把计算机的内存看作是一条长街上的一排房屋。每个房子都可以容纳数据,并通过一个放号标识。这样我们可以得出两件事情
①、内存中的每个位置都由一个独一无二的地址标识
②、内存中的每个位置都包含一个值
因此,我们知道一个内存地址的时候就可以访问这个地址中存取的值。但是要记住这些复杂的地址实在是太麻烦了,所以高级语言特性之一就是提供了通过名字而不是地址来访问内存的位置。当然要记住,名字和内存地址之间的关联不是硬件提供的,它是通过编译器实现的。
指针:指针是把内存地址作为其值的变量。变量通常包含一个具体的值,而指针包含的是拥有具体值的变量的地址
常量指针:
很多的例子都知道:声明常量指针的形式是有两种的:①:int const *p; ② const int *p;
这里关于这个叫法问题,我们可以把const这个词作为我们汉语中的‘常量’,这个*作为'指针'。这样只要const在前,*在后面就可以叫做 常量指针
常量指针我们可以理解为是把指针成为了一个常量,这样的指针只能从内存地址中读取出数据,而没法修改内存数据。
例1:
int main()
{
int i =4;
int const *p = &i; //按照上面叫法 常量指针
printf("%d ",*p);
p++; //这里仍然是没有错误的 不过输出的不是4了
printf("%x ",*p);
//*p = *p + 1; //ERROR 出错了 这里的*p是没法修改数据的,已经被保护了
printf("%d ",*p);
return 0;
}
例2:
int main() {
char *a = "abcde1234";
char *b = "qwert";
char const *d = b;
printf("%s ", d); //输出 qwert
d = a;
printf("%s ", d); //输出 abcde1234
d++;
// *d = "1234567890"; //这句不注释会出错,错误同上
printf("%s ", d); //输出 bcde1234
return 0; }
指针常量
和常量指针有点相反,他指向的位置不能改变,也就是指针本身是一个常量。但是指针常量可以同感间接引用来修改内存中的数据。
例3:
int main() {
int i =4; int j = 10;
int * const m = &j; //指针常量
printf("%d ",*m);
// m = &i; //指针常量地址不可变如同上面所说的,指针本事是一个常量因此地址不能变
*m = 8; //指针不能变,但是可以变的却是地址中的数据。
printf("%d ",*m);
return 0; }
同感两个例子我们可以发现,常量指针中int const *p; *p 定义初始化后是不能*p =8这样赋值的。因为在"常量指针"中我们不能改变这个指针所指向的内存地址中的值, 而指针常量就很明显了,不能改变这个指针的值,但是这个指针内存地址中的值却是可以改变的。