Chinaunix首页 | 论坛 | 博客
  • 博客访问: 616663
  • 博文数量: 201
  • 博客积分: 3076
  • 博客等级: 中校
  • 技术积分: 2333
  • 用 户 组: 普通用户
  • 注册时间: 2009-08-02 19:44
文章分类

全部博文(201)

文章存档

2010年(118)

2009年(83)

我的朋友

分类:

2010-05-14 19:23:28

#include

int main(int argc, char *argv[])
{
    int a[5] = {1, 3, 5, 7, 9};
    printf("%p,%p,%p\n", a, &a, &a[0]);
    int *p1 = a;
    int *p2 = (int*)&a;
    int (*p3)[5] = &a;
    printf("%d,%d,%d \n", *(p1+1), *(p2+1), *(*p3+1));

    int *p4 = (int*)(&a+2);
    int *p5 = (int*)((int)a+4);
    printf("%d,%d", p4[-6], *p5);
    return 0;
}


-----------------------------
语句2中,a和&a都是得到数组a的首元素的内存地址。把a 当作指向数组对象的首地址的指针,即为数组a的首元素的内存地址;而&a则是对数组对象取地址。
----------------------------------------------------------------------
a和&a都不是数组a首元素的地址!数组a首元素的地址是&a[0],a与&a所代表的地址值只不过跟&a[0]相同, 但意义和类型都是不同的,a是数组a的标识符,代表数组a,其类型是int[5],而&a是数组a的首地址,类型是int(*) [5],&a[0]的类型是int*,只不过因为地位特殊,地址值才与a、&a相同。


语句3中,用数组a去初始化指针p1,将数组a隐式转换为指针;
-------------------------------------------------
并非将a赋予p1的过程中a隐式转换为指针,而是a放在表达式中的时候已经隐式转换为指针了,a还没有赋予p1的时候,隐式转换已经完成了,a的类型从 int[5]转换为int*


语句4中,&a的类型为int (*) [5],即指向数组a[5]的指针,而在该句中,(int*)&a则将&a显式转换为int * 类型的指针,于是将p2初始化为指向数组的首元素的指针。
语句5中,p3为指向整形数组的指针,并用&a初始化,故*p3为p3指向的整形数组。
语句6中,*(p1+1),*(p2+1), *(*p3+1)的值都为3。
语句7中,&a+2将指向下两个元素。因为&a为指向数组a[5]的指针,故其实际移动的内存为两倍a[5]的内存(一个元素为20字 节,即40个字节),由a[5]的首元素地址向前移动40个字节,并将该地址赋值给p4(经过显式转换)。
语句8中,首先(int)a,将a显式转换成整形的值,加上4,实际上加了一个整形的地址长度,并将该地址赋值给p5(经过显式转换),实际上相当于移动 到数组的下一个元素。
语句9中,,p4[-6]即为*(p4-6),将p4向后移动了6个sizeof(int*) 的地址长度(24),于是移动到了数组中第5个元素的地址,所以,p4[-6]为9; *p5则为3.
------------------------------------------------------------------------
注意[-6]是符合标准的,标准规定下标运算的时候,步长的类型是int,因此可以是负数。
阅读(694) | 评论(0) | 转发(0) |
0

上一篇:mapreduce

下一篇:C Traps and Pitfalls

给主人留下些什么吧!~~