簡體   English   中英

取消引用並通過引用返回

[英]Dereference and return by reference

考慮一個小單元測試用例

struct A
{
   virtual void func(){}
   A& foo()
   {
     A *obj = reinterpret_cast<A*>(0xdeadbeef);
     return *obj; //1
   }
};

int main()
{
   A obj = obj.foo();
}

在第1行是實現定義/未指定,因為我們通過引用返回,所以不會發生deference,如果沒有對指向的對象進行顯式訪問,程序不會崩潰?

我與我的一位同事爭論過,他提到在大多數情況下,編譯器會優化obj的解引用,因為我們通過引用返回它並且這段代碼不會崩潰?

謝謝

我在MS VC8.0中反匯編代碼,發現更有趣的東西:

006D48D6  mov         dword ptr [ebp-8],ecx 
    A *obj = reinterpret_cast<A*>(0xdeadbeef);
006D48D9  mov         dword ptr [obj],0DEADBEEFh 
        return *obj; //1
006D48E0  mov         eax,dword ptr [obj] //2 
    }
006D48E3  mov         esp,ebp 
006D48E5  pop         ebp  
006D48E6  ret    

// 2表示只將obj的地址作為返回值放入eax寄存器。

006D39FC  lea         ecx,[ebp-190h] 
006D3A02  call        A::foo (6A8C12h) 
006D3A07  push        eax  //3
006D3A08  lea         ecx,[ebp-190h] 
006D3A0E  call        A::A (6B89BEh)

eax是0xdeadbeef,並且作為臨時局部變量推送到堆棧。 比我們調用復制構造函數(這是微不足道的)。 所有這些操作都只是傳遞地址(這是非法的,但程序不關心)。因為A結構沒有綁定到特定對象的任何成員,並且程序不會嘗試通過取消引用找到特定對象,如果它沒有因為這枚炸彈沒有被解雇。

        A *obj = reinterpret_cast<A*>(0xdeadbeef);
        A tmp ;
         temp = *obj;

即使這樣也可以,因為operator =也通過引用傳遞,實際上傳遞了地址。如果添加成員變量,它將失敗,因為它將嘗試查找並復制成員。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM