C++11 新特性 —— 关键字noexcept
轉(zhuǎn)載;https://www.cnblogs.com/sword03/p/10020344.html
1 關(guān)鍵字noexcept
從C++11開始,我們能看到很多代碼當中都有關(guān)鍵字noexcept。比如下面就是std::initializer_list的默認構(gòu)造函數(shù),其中使用了noexcept。
constexpr initializer_list() noexcept: _M_array(0), _M_len(0) { }該關(guān)鍵字告訴編譯器,函數(shù)中不會發(fā)生異常,這有利于編譯器對程序做更多的優(yōu)化。
如果在運行時,noexecpt函數(shù)向外拋出了異常(如果函數(shù)內(nèi)部捕捉了異常并完成處理,這種情況不算拋出異常),程序會直接終止,調(diào)用std::terminate()函數(shù),該函數(shù)內(nèi)部會調(diào)用std::abort()終止程序。
2 C++的異常處理
C++中的異常處理是在運行時而不是編譯時檢測的。為了實現(xiàn)運行時檢測,編譯器創(chuàng)建額外的代碼,然而這會妨礙程序優(yōu)化。
在實踐中,一般兩種異常拋出方式是常用的:
- 一個操作或者函數(shù)可能會拋出一個異常;
- 一個操作或者函數(shù)不可能拋出任何異常。
后面這一種方式中在以往的C++版本中常用throw()表示,在C++ 11中已經(jīng)被noexcept代替。
void swap(Type& x, Type& y) throw() //C++11之前{x.swap(y);}void swap(Type& x, Type& y) noexcept //C++11{x.swap(y);}3 有條件的noexcecpt
在第2節(jié)中單獨使用noexcept,表示其所限定的swap函數(shù)絕對不發(fā)生異常。然而,使用方式可以更加靈活,表明在一定條件下不發(fā)生異常。
void swap(Type& x, Type& y) noexcept(noexcept(x.swap(y))) //C++11{x.swap(y);}它表示,如果操作x.swap(y)不發(fā)生異常,那么函數(shù)swap(Type& x, Type& y)一定不發(fā)生異常。
一個更好的示例是std::pair中的移動分配函數(shù)(move assignment),它表明,如果類型T1和T2的移動分配(move assign)過程中不發(fā)生異常,那么該移動構(gòu)造函數(shù)就不會發(fā)生異常。
pair& operator=(pair&& __p)noexcept(__and_<is_nothrow_move_assignable<_T1>,is_nothrow_move_assignable<_T2>>::value){first = std::forward<first_type>(__p.first);second = std::forward<second_type>(__p.second);return *this;}4 什么時候該使用noexcept?
使用noexcept表明函數(shù)或操作不會發(fā)生異常,會給編譯器更大的優(yōu)化空間。然而,并不是加上noexcept就能提高效率,步子邁大了也容易扯著蛋。
以下情形鼓勵使用noexcept:
- 移動構(gòu)造函數(shù)(move constructor)
- 移動分配函數(shù)(move assignment)
- 析構(gòu)函數(shù)(destructor)。這里提一句,在新版本的編譯器中,析構(gòu)函數(shù)是默認加上關(guān)鍵字noexcept的。下面代碼可以檢測編譯器是否給析構(gòu)函數(shù)加上關(guān)鍵字noexcept。
- 葉子函數(shù)(Leaf Function)。葉子函數(shù)是指在函數(shù)內(nèi)部不分配棧空間,也不調(diào)用其它函數(shù),也不存儲非易失性寄存器,也不處理異常。
最后強調(diào)一句,在不是以上情況或者沒把握的情況下,不要輕易使用noexception。
總結(jié)
以上是生活随笔為你收集整理的C++11 新特性 —— 关键字noexcept的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 关于西门子plc的CPU
- 下一篇: 将GDB中的输出定向到文件