/Zc:throwingNew (假設擲回運算子 new)
指定 /Zc:throwingNew 選項時,編譯程式會將 呼叫優化為 operator new
,以略過 Null 指標傳回的檢查。 此選項會告知編譯程序假設 和 自定義配置器的所有鏈接實 operator new
作都符合C++標準,並在配置失敗時擲回。 根據預設,在 Visual Studio 中,編譯程式會悲觀地產生這些呼叫的 Null 檢查(/Zc:throwingNew-),因為使用者可以連結至傳回 Null 指標的非 operator new
擲回實作或寫入傳回 Null 指標的自定義配置器例程。
語法
/Zc:throwingNew[-]
備註
由於 ISO C++98,標準已指定當記憶體配置失敗時,預設 運算符 new 會 std::bad_alloc
擲回。 Visual C++高達 Visual Studio 6.0 的版本在配置失敗時傳回 Null 指標。 從 Visual Studio 2002 開始, operator new
符合標準,並在失敗時擲回。 為了支援使用舊版配置樣式的程序代碼,Visual Studio 提供 nothrownew.obj 中可連結的 operator new
實作,以在失敗時傳回 Null 指標。 根據預設,編譯程式也會產生防禦性 Null 檢查,以防止這些舊式配置器在失敗時立即當機。 /Zc:throwingNew 選項會告知編譯程式排除這些 Null 檢查,假設所有連結的記憶體配置器都符合標準。 這不適用於明確非擲回 operator new
的多載,這些多載是使用 型 std::nothrow_t
別的其他參數來宣告,而且具有明確的 noexcept
規格。
就概念上講,若要在免費存放區上建立對象,編譯程式會產生程式代碼來配置其記憶體,然後叫用其建構函式來初始化記憶體。 因為 MSVC 編譯程式通常無法判斷此程式代碼是否會連結至不符合規範的非擲回配置器,因此它預設也會在呼叫建構函式之前產生 Null 檢查。 如果非擲回的配置失敗,這可防止建構函式呼叫中的Null指標取值。 在大部分情況下,這些檢查都是不必要的,因為預設 operator new
配置器會擲回,而不是傳回 Null 指標。 檢查也有不幸的副作用。 它們會膨脹程序代碼大小、淹沒分支預測值,並禁止其他有用的編譯程序優化,例如將虛擬化或 const 傳播移出初始化的物件。 檢查只支持連結至 nothrownew.obj 或具有自定義不符合 operator new
規範實作的程序代碼。 如果您未使用不符合 operator new
規範,建議您使用 /Zc:throwingNew 將程式代碼優化。
/Zc:throwingNew 選項預設為關閉,而且不會受到 /permissive- 選項的影響。
如果您使用鏈接時間程式代碼產生 (LTCG) 進行編譯,則不需要指定 /Zc:throwingNew。 使用 LTCG 編譯程式代碼時,編譯程式可以偵測是否使用預設且符合規範的 operator new
實作。 如果是,編譯程式會自動排除 Null 檢查。 鏈接器會尋找 /ThrowingNew 旗標,以判斷 的 operator new
實作是否符合規範。 您可以將這個旗標指定給連結器,方法是在自訂運算子新實作的來源中包含這個指示詞:
#pragma comment(linker, "/ThrowingNew")
如需 Visual C++ 中一致性問題的詳細資訊,請參閱 Nonstandard Behavior。
在 Visual Studio 開發環境中設定這個編譯器選項
開啟專案的 [屬性頁] 對話方塊。 如需詳細資料,請參閱在 Visual Studio 中設定 C ++ 編譯器和組建屬性。
從 [ 組態 ] 下拉功能表中,選擇 [ 所有組態]。
選取 [組態屬性]>[C/C++]>[命令列] 屬性頁。
修改 [其他選項] 屬性以包含 /Zc:throwingNew 或 /Zc:throwingNew- ,然後選擇 [確定]。
另請參閱
MSVC 編譯器選項
MSVC 編譯器命令列語法
/Zc (一致性)
noexcept (C++)
例外狀況規格 (throw) (C++)
terminate (exception)