免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
123下一页
最近访问板块 发新帖
查看: 2576 | 回复: 21
打印 上一主题 下一主题

搞不懂GCC的形为,关于类成员偏移量的输出. [复制链接]

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2004-08-15 12:58 |只看该作者 |倒序浏览
  1. #include <iostream>;
  2. #include <stdio.h>;
  3. using namespace std;
  4. struct A{
  5.    char ch;
  6.    int i;
  7.    int k;
  8. };

  9. int main()
  10. {
  11.    printf("%p\n",&A::ch);
  12.    printf("%p\n",&A::i);
  13.    printf("%p\n",&A::k);
  14.    cout << &A::ch << endl;
  15.    cout << &A::i << endl;
  16. }
复制代码
0x0
0x4
0x8
1
1
这是结果.
1>;为什么指向A数据成员的指针并没有重载<<操作符它还可以编译通过呢?而且GCC还输入1是怎么回事?

2>;为什么前面三个是0.4.8?我觉得应该是0,1,5呀.我想是在char ch后面有3bytes的补齐.但为什么是在ch成员后直接补齐而不是在整个数据成员所占内存后补呢?我觉得应该是1byte+4byte+4byte+3byte(补的)

3>;本来的输出应该是1,5,9,是吧,但由于编译器的特殊处理使得类数据成员的偏量都没有增加1.不知这个"特殊处理"是怎么个特殊法.

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
2 [报告]
发表于 2004-08-15 13:18 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

  1. #include <iostream>;
  2. using namespace std;
  3. #include <cstdio>;

  4. struct Base1 { int val1;};
  5. struct Base2 { int val2;};
  6. struct Derived : Base1,Base2 { };

  7. void f1(int Derived::*dmp, Derived *pd)
  8. {
  9.    pd->;*dmp;
  10. }

  11. void f2(Derived *pd)
  12. {
  13.    int Base2::*bmp = &Base2::val2;
  14.    f1(bmp,pd);
  15. }

  16. int main()
  17. {
  18.    printf("%p\n", &Base1::val1);
  19.    printf("%p\n",&Base2::val2);
  20.    printf("%p\n",&Derived::val1);
  21.    printf("%p\n",&Derived::val2); //4
  22. }
复制代码
再看看这个程序.为什么4处输出的也是0?书上只说"是否编译器已经内部处理过了呢?很可能(我只能猜测)".大家怎么认为?是不是没有必要研究这种问题?

论坛徽章:
0
3 [报告]
发表于 2004-08-15 18:01 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

0,4,8 is 4 bytes aligned, but 0,1,5 is NOT.
4 bytes aligned means the address can be divided by 4

论坛徽章:
0
4 [报告]
发表于 2004-08-15 18:02 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

Read assembly generated from the cpp, you'll know the truth.

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
5 [报告]
发表于 2004-08-15 21:27 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

原帖由 "mep" 发表:
0,4,8 is 4 bytes aligned, but 0,1,5 is NOT.
4 bytes aligned means the address can be divided by 4

我不懂汇编.所以....看不懂产生的汇编码.希望以后能补上这一课.
什么?4字节对齐?什么意思?有这样的?我不太能明白你的意思.
不过我的几个问题是不是只用这一句话就能解释?

论坛徽章:
0
6 [报告]
发表于 2004-08-15 22:30 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

要想学好C,首先要学好汇编。不打好基础,学再多的知识也是空中楼阁。
你可以看看这个,如果不能理解,说明你需要弥补你的基础知识。
http://www.linuxsir.org/bbs/showthread.php?s=&threadid=47160&perpage=15&pagenumber=6

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
7 [报告]
发表于 2004-08-15 22:56 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

先不说对齐吧.(我正在看).回复一下再说.
第一帖中的第三个问题和第二帖中的问题和对齐没关系.
应该如何解释呢?

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
8 [报告]
发表于 2004-08-15 22:59 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

原帖由 "kj501" 发表:
要想学好C,首先要学好汇编。不打好基础,学再多的知识也是空中楼阁。
你可以看看这个,如果不能理解,说明你需要弥补你的基础知识。
http://www.linuxsir.org/bbs/showthread.php?s=&threadid=47160&perpage=15&p..........

很多C++高手也不懂汇编的...当然大师级人物一般还是懂的吧.

论坛徽章:
1
荣誉版主
日期:2011-11-23 16:44:17
9 [报告]
发表于 2004-08-15 23:13 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

》》printf("%p\n",&A::ch);
这种形式打印的是ch变量在class中的offset,
也就是一个非负整数,为什么要重载呢?
2。弄明白这个问题,你要知道对齐的概念,
为什么要对齐,对齐有什么好处,明白了这个,
你的答案也就有了。
3。我没看懂,我也没环境试验一下。
还有第二个贴子,呵呵,说一下我的意见,
有时候有些东西就要不求甚解,要想彻底搞清楚
真的很难很难。除非你特别感兴趣,或者有充分的时间,
或者你的工作要求你必须清楚。

论坛徽章:
1
荣誉会员
日期:2011-11-23 16:44:17
10 [报告]
发表于 2004-08-15 23:46 |只看该作者

搞不懂GCC的形为,关于类成员偏移量的输出.

原帖由 "lenovo" 发表:
》》printf("%p\n",&A::ch);
这种形式打印的是ch变量在class中的offset,
也就是一个非负整数,为什么要重载呢?
2。弄明白这个问题,你要知道对齐的概念,
为什么要对齐,对齐有什么好处,明白了这个,
你的答案也就有了。
3。我没看懂,我也没环境试验一下。
还有第二个贴子,呵呵,说一下我的意见,
有时候有些东西就要不求甚解,要想彻底搞清楚
真的很难很难。除非你特别感兴趣,或者有充分的时间,
或者你的工作要求你必须清楚。

1>;我是讲用cout << &A::ch;就不行.不过G++可以通过.VC5不行.
报错信息说是没有重载<<.
2>;正在补.
3>;

说的也是.

TO:kj501
你说的很好.学习.要把握分寸.
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP