簡體   English   中英

檢查我對功能返回的理解

[英]Checking my understanding about function return

作為一個新手,我發現在C ++書籍中從函數返回的解釋相當神秘。

以下是我理解的摘要,希望有人可以糾正它:

物業:

T foo() {
   ...
   return expr;
}

main() {
   T var = foo();
}

我對回歸過程的理解是否正確?

  1. expr的求值結果被隱式轉換為聲明的函數返回類型T 這種轉換發生 foo();
  2. 上面轉換的值用於初始化臨時對象,比如“x”。 子問題:第二次轉換是在foo()還是main()中發生的?
  3. 臨時對象“x”用於初始化main()中的變量var

歡迎任何輸入!

讓我們系統地解決這個問題。

如果函數聲明為T f(); ,並且T不是void ,如果函數正常返回,那么它必須通過表單return e; ,其中e是一些表達。

當您計算函數調用表達式f() ,您將獲得一個值。 假設U表示對象類型。 如果T = U &T = U && ,則該值為U類型,表達式e必須能夠綁定到引用,返回值 e的值。 (就其價值類別而言,返回值也是所謂的“glvalue”)。 在這種情況下沒有其他事情發生。 函數調用的值是返回的東西。

但是,當T = Uf()的值是所謂的“prvalue”(“純rvalue”),這就需要構造U臨時對象 該對象被構造為好像通過U obj = e (即從e隱式轉換)。 然后f()的值就是這個臨時對象。 它可以用於初始化另一個對象(例如U x = f(); ),也可以綁定到引用(例如U && r = f(); )。

返回表達式e與函數調用值的綁定作為函數體范圍內的最后一件事發生。 值得注意的是,這是范圍結束之前 ,即在范圍本地對象被銷毀之前。 例如,如果在構造返回值對象期間拋出異常,則在異常傳遞給調用范圍之前,必須發生范圍展開以銷毀本地對象。 另一個有用的例子可能是使用范圍保護,例如互斥鎖:

U f()
{
    std::locK_guard<std::mutex> lock(state_mutex);
    return state.get_value();
}

這里我們假設初始化U obj = state.get_value(); 是有道理的,我們進一步假設只有在state_mutex被鎖定時才能調用state.get_value() 上面的代碼正確而簡潔地完成了這一過程。

  1. 你是對的,隱式轉換發生在foo 考慮何時有多個return語句,每個返回一個不同的類型 - 必須先轉換所有這些類型,然后才能返回一個值。
  2. 沒有第二次轉換。 第一次轉換是臨時建設或轉讓的一部分。
  3. 正確,除非下面解釋。

有一個優化,許多編譯器將稱為復制省略 ,完全跳過臨時。

你的理解基本上是正確的。
可以進行一些優化,因此沒有那么多步驟
復制。 這可以是return value optimization的形式,也可以是
在c ++ 11中move semantics

關於你的子問題;
在自定義轉換運算符,構造函數中,您既不應該假設
破壞者等

暫無
暫無

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

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