什么是內聯命名空間?C ++ 11允許inline namespaces,其所有成員也自動在封閉中namespace。我想不出任何有用的應用 - 有人可以給出一個簡短,簡潔的例子,說明inline namespace需要哪種情況以及最常用的解決方案?(另外,當發生了什么并不清楚,我namespace聲明inline在一個但不是所有的聲明,這可能住在不同的文件。這難道不是找麻煩?)
3 回答

aluckdog
TA貢獻1847條經驗 獲得超7個贊
除了上面的所有答案。
內聯命名空間可用于編碼符號中的ABI信息或函數版本。正是由于這個原因,它們被用于提供后向ABI兼容性。內聯命名空間允許您在不更改API的情況下將信息注入到損壞的名稱(ABI)中,因為它們僅影響鏈接器符號名稱。
考慮這個例子:
假設您編寫了Foo
一個引用對象的函數,bar
并且不返回任何內容。
在main.cpp中說
struct bar;void Foo(bar& ref);
如果在將文件編譯為對象后檢查此文件的符號名稱。
$ nm main.o T__ Z1fooRK6bar
鏈接器符號名稱可能會有所不同,但它肯定會在某處編碼函數和參數類型的名稱。
現在,它可能被bar
定義為:
struct bar{ int x;#ifndef NDEBUG int y;#endif};
根據構建類型,bar
可以引用具有相同鏈接器符號的兩種不同類型/布局。
為了防止這種行為,我們將結構包裝bar
到一個內聯命名空間中,根據Build類型,鏈接器符號bar
將是不同的。
所以,我們可以寫:
#ifndef NDEBUGinline namespace rel { #elseinline namespace dbg {#endifstruct bar{ int x;#ifndef NDEBUG int y;#endif};}
現在,如果您查看每個對象的目標文件,您可以使用release構建一個,另一個使用debug flag。您會發現鏈接器符號也包含內聯命名空間名稱。在這種情況下
$ nm rel.o T__ ZROKfoo9relEbar$ nm dbg.o T__ ZROKfoo9dbgEbar
鏈接器符號名稱可能不同。
注意符號名稱的存在rel
和dbg
符號名稱。
現在,如果您嘗試將調試與發布模式鏈接或反之亦然,則會出現鏈接器錯誤,這與運行時錯誤相反。
- 3 回答
- 0 關注
- 891 瀏覽
添加回答
舉報
0/150
提交
取消