C语言数组指针与指针数组

1.指针数组
指针数组是一个存放指针的数组
int* arr1[10]; //整形指针的数组
char *arr2[4]; //一级字符指针的数组
char **arr3[5];//二级字符指针的数组
2.数组指针
首先,先要了解数组指针不是一个数组,而是一个指针, 数组指针是指向数组的指针
形如  int ( * p )[ 10 ] 则是数组指针
3. & 数组名
对于 int arr[10];
如果对其分别打印&arr和arr的地址,可以得到
得到两个地址是相同的,但两者的意义是完全不同的,在对其进行&arr+1和arr+1取地址,得到如果如下

 

两个地址相差36,为16*2+4;其原因是因为&符号是将整个数组当做一个整体,再取其地址,也就是整个数组的首地址,而直接arr取得的地址是这个数组的首元素的首地址.倘若进行&arr+1操作,则是跳过整个数组,取得的地址就要在原有的地址上加上整个数组所占的字节数,而进行arr+1操作,只要在原基础上加上一个 int所占的字符数就可以.

 4.函数指针

函数指针是一个指向函数的指针

形如void ( * pfun1 )() 是一个函数指针,其原因是 pfun1可以存放。pfun1先和*结合,说明pfun1是指针,指针指向的是一个函数,指向的函数无参数,返回值类型为void。
 5.函数指针数组
形如  int ( * parr [ 10 ])(); 则是一个函数指针数组
parr  先和 [] 结合,说明 parr 是数组,数组的内容是 int (*)() 类型的函数指针。

接下来 进行一组练习题

1.int main()

{
    int a [ 5 ] = { 1 , 2 , 3 , 4 , 5 };
    int * ptr = ( int * )( & a + 1 );
    printf ( "%d,%d" , * ( a + 1 ), * ( ptr - 1 ));
    return 0 ;
}

 此代码的输出结果是2,5

其原因是a是元素的首元素地址,所以a+1是先将a进行隐式转换成指针a,在进行加一操作,得到此数组里第二个元素的地址,在进行*解引用操作,得到值为2

而&a是将数组a当做一个整体,取整个数组的地址,在进行加一操作,就是跳过整个数组,指针直接指向这个数组之后的第一个地址,在进行强制类型转换为int*类型,当ptr-1时,就是指这个指针向后偏移一个int ,指向了数组的最后一个元素5,在进行*操作,得到了结果为5.

2.
struct Test
{
int Num ;
char * pcName ;
short sDate ;
char cha [ 2 ];
short sBa [ 4 ];
} * p = (struct test*)0x100000 ;
int main ()
{
printf ( "%p\n" , p + 0x1 );
printf ( "%p\n" , ( unsigned long ) p + 0x1 );
printf ( "%p\n" , ( unsigned int* ) p + 0x1 );
return 0 ;

 }

 

第一个结果为0x100014,其原因是因为p+0x1 就是将结构体指针p当做一个整体,并且跳过整个结构体,结构体的大小事20个字节,所以为0x100014;特别注意的是20个字节要转成16进制的数字,所以为14

第二个结果为00100001,其原因是(unsigned long)p结构体指针强制转换为一个long类型的整数,整数进行+1操作,得到00100001

第三个结果是因为(unsigned int*)p将将这个结构体指针强制转换为一个无符号的int* 类型,占四个字节,所以为0010004

3.

int main ()
{
    int a [ 4 ] = { 1 , 2 , 3 , 4 };
    int * ptr1 = ( int * )( & a + 1 );
    int * ptr2 = ( int * )(( int ) a + 1 );
    printf ( "%x,%x" , ptr1 [ - 1 ], * ptr2 );
    return 0 ;  
}
第一个结果的原因是&arr+1是指向这个数组向后的一个地址,在强制转换为一个int*类型,在打印的时候ptr[-1]相当于指针向前移动一个元素,指向了4

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值