目录
测试题1
#include <stdio.h>
int main()
{
int a[5] = {1,2,3,4,5};
int *ptr = (int *)(&a + 1); //&a代表取得是整个数组的地址,+1后指向跳过整个数组,将他强转为(int *)并赋给ptr
printf("%d,%d\n",*(a + 1),*(ptr - 1));//输出为 2,5
//(a + 1)只想第二个元素的地址,解引用得2
//*(ptr - 1)将指针-1后,变为了a[4],解引用 得出5
return 0;
}
测试题2
#include <stdio.h> //测试题2 //假设p 的值为0x100000。如下表达式的值分别为多少? //已知,结构体Test类型的变量大小是20个字节 struct Test { int Num; char *pcName; short sDate; char cha[2]; short sBa[4]; }*p; int main() { p = (struct Test*)0x100000; printf("%p\n",p + 0x1);//0x1代表十六进制的1 +1,加在了指针上,越过了整个结构体 所以为 0x100014 printf("%p\n",(unsigned long )p + 0x1);//将p强转为数字1048576,+1加在了数值上得1048577 即0x100001 printf("%p\n",(unsigned int*)p + 0x1);//将p强转为无符号int*的指针,+1,unsigned int 通常是 4 个字节,0x1代表4个字节 }
测试题3
#include <stdio.h> //测试题3 int main() { int a[4] = {1,2,3,4}; int *ptr1 = (int*)(&a + 1); //&a代表整个数组的大小,+1后指向数组后边那个地址,(int*)将其装换为数值指针,用ptr1接收 int *ptr2 = (int*)((int)a + 1); //a是指针,(int)a代表转化为int类型数值,+1,即数值加一, // 就比如:0x00 00 00 05 +1后转为 // 0x00 00 00 06 //以下在内存中(小端存储)表示 // 01 00 00 00 | 02 00 00 00 | 03 00 00 00 | 04 00 00 00 ... //^(开始指向位置) // ^(偏移后)此时指针指向 //于是4个字节为一个字符 //00 00 00 02 | 00 00 00 ....... // 后将其转化为(int*)类型的指针,指针偏移一个字节,赋值给ptr2 //转为16进制整数 20 00 00 00 的地址 printf("%x,%x",ptr1[-1],*ptr2); //ptr1[-1] == *(ptr1+(-1)) == *(ptr1-1) //于是ptr1[-1] == 4 return 0; }
测试题4
#include <stdio.h> //测试题5 int main() { int a[5][5]; int(*p)[4];//数组指针 p = a;//这里会报警告 因为p的类型是int(*)[4] --- a的类型是 int [5] //p[4][2] == *(*(p+4)+2) printf("%p,%d\n",&p[4][2] - &a[4][2] , &p[4][2] - &a[4][2]);//输出结果 为FFFFFFFFFFFFFFFC,-4 //通过图像可知 相差为 4 个元素 ,即如下十六进制的地址计算 //1000 0000 0000 0000 0000 0000 0000 0100 //1111 1111 1111 1111 1111 1111 1111 1011 //1111 1111 1111 1111 1111 1111 1111 1100 //以%p来打印,编译器就认为我这里放的是地址,输出: // F F F F F F F C }
测试题5
#include <stdio.h> //测试题6 int main() { int aa[2][5] = {1,2,3,4,5,6,7,8,9,10}; //&aa + 1 代表指针 ,跳过了第二行的整个数组 //将数组指针强转为int*指针 ,赋值给*ptr1 int *ptr1 = (int*)(&aa + 1); //aa + 1 == aa[1]表示第二行数组整个数组,aa[1]找到数组名,解引用找到第二行第一个元素地址 int *ptr2 = (int*)(*(aa + 1)); //如下图所示: printf("%d,%d",*(ptr1 - 1),*(ptr2 - 1));//输入结果为 10,5 return 0; }
测试题6
#include<stdio.h> //测试题6 int main() { //(0,1),(2,3),(4,5) 逗号表达式,从放了1,2,3 int a[3][2] = {(0,1),(2,3),(4,5)}; int *p; p = a[0]; //p[0] == *(p + 0) printf("%d",p[0]);//输出为 1 return 0; }
测试题7
#include <stdio.h> //测试题7 int main() { char *a[] = {"work","at","alibaba"}; //这个a指针数组里边存放的 是 w a a 的首地址 //将a 赋值给 char** 就是将pa指向指针数组a的首地址 //如下图解释: char**pa = a; //pa++就是指向指针数组的第二个元素的地址 pa++; //解引用操作,找到指针数组的第二个元素的内容,打印字符串 printf("%s\n",*pa);//输出 at return 0; }
测试题8
#include <stdio.h> //测试题8 int main() { char* c[] = {"ENTER","NEW","POINT","FIRST"}; char**cp[] = {c+3,c+2,c+1,c}; char***cpp = cp; printf("%s\n",**++cpp); printf("%s\n",*--*++cpp + 3); printf("%s\n",*cpp[-2] + 3);//* *(cpp + (-2)) + 3 其中cpp的指向位置是不变的 printf("%s\n",cpp[-1][-1] + 1);//*( *(cpp - 1) -1 ) + 1 这里的指针指向改变( *(cpp - 1) -1 ) return 0; }