您的位置:首页 > 编程语言 > C语言/C++

C++中的引用在初始化时占用内存吗?

2015-08-25 15:35 633 查看
这个问题,还没有完全研究完,先贴上一部分实验结果。

这里比较疑惑的有两个问题,c++中是怎么实现引用的和引用会和指针一样占用内存吗?

其实是一个问题,下面的实验都是在linux64 g++编译器平台

看第一段代码

#include<iostream>
using namespace std;

int main()
{
int a=10;
int* p =&a;
int &q =a;

cout<<&a<<endl;
cout<<&p<<endl;
cout<<&q<<endl;

(*p)++;
q++;
cout<<a<<endl;
return 0;
}


三个cout是将变量的地址打印出来

结果是

0x7fffffffe32c
0x7fffffffe330
0x7fffffffe32c
12


表面上看引用和变量是一个地址,看看目标代码的反汇编代码

int main()
{
40087d:   55                      push   %rbp
40087e:   48 89 e5                mov    %rsp,%rbp
400881:   48 83 ec 20             sub    $0x20,%rsp
int a=10;
400885:   c7 45 ec 0a 00 00 00    movl   $0xa,-0x14(%rbp)
int* p =&a;
40088c:   48 8d 45 ec             lea    -0x14(%rbp),%rax
400890:   48 89 45 f0             mov    %rax,-0x10(%rbp)
int &q =a;
400894:   48 8d 45 ec             lea    -0x14(%rbp),%rax
400898:   48 89 45 f8             mov    %rax,-0x8(%rbp)

cout<<&a<<endl;
40089c:   48 8d 45 ec             lea    -0x14(%rbp),%rax
4008a0:   48 89 c6                mov    %rax,%rsi
4008a3:   bf 80 10 60 00          mov    $0x601080,%edi
4008a8:   e8 b3 fe ff ff          callq  400760 <_ZNSolsEPKv@plt>
4008ad:   be 80 07 40 00          mov    $0x400780,%esi
4008b2:   48 89 c7                mov    %rax,%rdi
4008b5:   e8 b6 fe ff ff          callq  400770 <_ZNSolsEPFRSoS_E@plt>
cout<<&p<<endl;
4008ba:   48 8d 45 f0             lea    -0x10(%rbp),%rax
4008be:   48 89 c6                mov    %rax,%rsi
4008c1:   bf 80 10 60 00          mov    $0x601080,%edi
4008c6:   e8 95 fe ff ff          callq  400760 <_ZNSolsEPKv@plt>
4008cb:   be 80 07 40 00          mov    $0x400780,%esi
4008d0:   48 89 c7                mov    %rax,%rdi
4008d3:   e8 98 fe ff ff          callq  400770 <_ZNSolsEPFRSoS_E@plt>
cout<<&q<<endl;
4008d8:   48 8b 45 f8             mov    -0x8(%rbp),%rax
4008dc:   48 89 c6                mov    %rax,%rsi
4008df:   bf 80 10 60 00          mov    $0x601080,%edi
4008e4:   e8 77 fe ff ff          callq  400760 <_ZNSolsEPKv@plt>
4008e9:   be 80 07 40 00          mov    $0x400780,%esi
4008ee:   48 89 c7                mov    %rax,%rdi
4008f1:   e8 7a fe ff ff          callq  400770 <_ZNSolsEPFRSoS_E@plt>
。。。。。
}


主要看这段代码

int &q =a;
400894:   48 8d 45 ec             lea    -0x14(%rbp),%rax
400898:   48 89 45 f8             mov    %rax,-0x8(%rbp)


实际q这个所谓的别名是占有内存的,

那么为什么输出其地址时,输出的引用变量的地址,看看反汇编代码就知道了

cout<<&q<<endl;
4008d8:   48 8b 45 f8             mov    -0x8(%rbp),%rax
cout<<&p<<endl;
4008ba:   48 8d 45 f0             lea    -0x10(%rbp),%rax


看看这两者的区别,对于取引用地址,是获取的原变量的地址,而取指针地址,则是将自己的内存地址输出去。

为了进一步说明这个问题 ,再用一段代码

struct  test1
{
int a;
int& p;
};
struct test2
{
int a;
};
struct test3
{
int a;
int* p;
};
int main()
{
cout<<sizeof(test1)<<endl;
cout<<sizeof(test2)<<endl;
cout<<sizeof(test3)<<endl;
}


运行结果为

16

4

16

好像看来引用是占内存的。。

可是真实这样吗?。。。。。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: