衆所周知,該標準C++ 11保證傳遞給函數的臨時對象將被之前的函數調用創建:Does standard C++11 guarantee that temporary object passed to a function will have been created before function call?標準C++ 11是否保證傳遞給函數的臨時對象在函數結束後會被銷燬?
但是,沒有標準的C++ 11保證傳遞給函數的臨時對象將有功能結束後(而不是之前)被銷燬?
工作草案,標準編程語言C++ 2016年7月12日:http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2016/n4606.pdf
§12.2的臨時對象
§12.2/5
有三個背景中的臨時的在完整表達式的結尾的 不同點處銷燬。第一個上下文 是調用缺省構造函數以初始化沒有相應初始化程序(8.6)的 數組的元素。第二個上下文是 ,當複製構造函數被調用來複制數組的一個元素時, 整個數組被複制(5.1.5,12.8)。在任何一種情況下,如果 構造函數具有一個或多個默認參數,則在構造下一個數組元素(如果有)之前,對在默認參數中創建的每個臨時文件的銷燬進行排序。當引用被綁定到臨時時,第三上下文是 。
另外:
§1.9/10
甲全表達是不是 另一表達子表達式的表達式。 [注意:在某些情況下,如未評估的 操作數,語法子表達式被認爲是全表達式 (第5章)。 - 結束註釋]如果語言結構被定義爲產生一個函數的隱式調用,則爲了該定義的目的,語言結構的使用被認爲是一個表達式。 A 調用除了臨時對象以外的對象 的生命週期結束時生成的析構函數是隱式的完整表達式。 爲了滿足 表達式 顯示的語言結構的要求,應用於表達式結果的轉換也被認爲是完整表達式的一部分。
這是否意味着標準C++ 11保證傳遞給函數的臨時對象在函數結束之前不會被破壞 - 而且恰好在完整表達式的結尾?
#include <iostream>
using namespace std;
struct T {
T() { std::cout << "T created \n"; }
int val = 0;
~T() { std::cout << "T destroyed \n"; }
};
void function(T t_obj, T &&t, int &&val) {
std::cout << "func-start \n";
std::cout << t_obj.val << ", " << t.val << ", " << val << std::endl;
std::cout << "func-end \n";
}
int main() {
function(T(), T(), T().val);
return 0;
}
輸出:
T created
T created
T created
func-start
0, 0, 0
func-end
T destroyed
T destroyed
T destroyed
,我們可以說,T destroyed
永遠是func-end
後?
而且這樣的:
function(T(), T(), T().val);
是總是等於這個:
{
T tmp1; T tmp2; T tmp3;
function(tmp1, tmp2, tmp3.val);
}
你的最後一部分以「這和:」開頭是不正確的,沒有。 (逗號運算符的左對齊不適用於函數參數。)期待這個好問題的正確答案。 – Bathsheba
你不相信我的回答嗎? – NathanOliver
@Bathsheba謝謝!錯字固定。 – Alex