这几天在复习数据结构的内容,然后就想着回顾回顾指针的内容了 QAQ
指针
#include<stdio.h>
void test01(){
int a = 100;
printf("%p \n",&a); // &a 取a的地址,但是a是int型的,拥有4个字节(1个字节 = 8位)
printf("%d \n",&a); // 2686728 10进制(等于28ff08) 这里打印的只是a第1段地址的起点
// 每一个字节对应一个地址,也就是说存放a是需要4个地址的
// 4个地址分别是 2686728(第1段)2686729(第2段)26867230(第3段)2686731(第4段)2686732
int* p = &a; // 定义一个指针变量,存储a的地址
// (或者说是定义一个int* 型的变量,指向int型的地址,大小(或者说是跨度)为4个字节)
printf("%d \n",sizeof(p)); // p的大小是4(单位:字节)
printf("%p \n",p); // 28ff08 16进制
printf("%p \n",p+1); // 28ff08 + 1(*4) = 28ff0c
printf("%d \n",p); // 2686728 10进制
printf("%d \n",p+1); // 2686728 + 1(*4) = 2686732
printf("%d \n",*p); // * 号代表:取该变量的值所对应空间的内容
*p = 0x10203040; // 4个字节 (10 20 30 40)
printf("%x \n",*p); // 10203040
short* sh = (short*)p; // 定义一个 short* 类型的指针变量,指向short型的地址(大小为2个字节)
printf("%x \n",*sh); // 3040 可以看到sh只拿到了p 2个字节的数据(头0不显示)
char* ch = (char*)p; // 定义一个 char* 类型的指针变量,指向char型的地址(大小为1个字节)
printf("%x \n",*ch); // 40 可以看到s只拿到了p 1个字节的数据(头0不显示)
//那怎么拿到p 最高位的2个字节数据呢?
// 答:根据跨度取地址
//前面已经知道了p的地址段有4段,分别存放4个字节的数据
// 2686728(第1段)2686729(第2段)26867230(第3段)2686731(第4段)2686732
// 10 20 30 40
//如果直接 short* sh = (short*)p; 那么得到的便是从 2686728 开始的地址(short的跨度为2)
short* sh11 = (short*)p+1; // 取p地址跨过1个short大小(2个字节)的地址
printf("%x \n",*sh11); // 1020 可以看到sh拿到了p 前2个字节的数据(头0不显示)
int **p1; //定义一个 int** 类型的指针变量,指向int* 型的地址
}
int main(){
test01();
return 0;
}
野指针
int* p; //指向未知地址
空指针
int* p = NULL; //指向0地址
修改指针对应空间存放的数据
如果你要对一个函数传入一个指针p,相当于传入了一个地址进去,如果你对这个地址对应的空间数据进行更改,那么p对应的值也会被改变了。
#include<stdio.h>
void fun(int* t);
int main(){
int a = 10;
int *p = &a;
printf("fun函数调用前 p = %d \n",*p);
fun(p);
printf("fun函数调用后 p = %d",*p);
return 0;
}
void fun(int* t){
*t = 20;
}
注意:是修改地址对应的空间数据,而不是改变这个指针,毕竟你传参数进去,就相当于在栈空间又定义了一个指针变量t来接受这个值而已,你改变了t的值,就并非操控了原来的p的地址了。而函数结束后,这个变量t又由系统自动释放掉了。
错误示范:
#include<stdio.h>
void fun(int* t);
int main(){
int a = 10;
int *p = &a;
printf("fun函数调用前 p = %d \n",*p);
fun(p);
printf("fun函数调用后 p = %d",*p);
return 0;
}
void fun(int* t){
int n = 1000;
t = &n;
}
修改指针值
当然,如果要修改指针的话,也是可以的,不过要传引用,这样相当于,你传一个地址进去,栈空间又定义了一个指针变量的引用t来接受这个地址(相当于k的别名),接着这个t值的更改,等于k的更改。
#include<stdio.h>
#include<malloc.h>
void fun(int* &t){
int n =1000;
t = &n;
}
int main(){
int *p = (int*)malloc(sizeof(int));
*p = 10;
int *&k = p;
printf("fun函数调用前 k = %d \n",*k);
fun(k);
printf("fun函数调用后 k = %d",*k);
return 0;
}
指针的大小
指针的大小与类型无关,只与操作系统有关,32位系统的指针都占4个字节,64位指针占8个字节
可以顺便看一下引用的知识:https://blog.csdn.net/piano_diano/article/details/103101506
PS:上面的部分代码是看了传智的视频写的,后续有时间还会补上其他一些内容