透過值和隱式移動規則傳回命名物件
在 C 中,可以透過引用或透過函數從函數傳回物件價值。當按值返回時,物件被複製或移動,具體取決於上下文。當從臨時物件的函數按值傳回物件時,將套用隱式移動規則。
範例1:移動建構子
考慮下面的範例:
<code class="cpp">class test { public: test(int y) { printf("test(int y)\n"); } test() { printf("test()\n"); } test(const test& z) { printf("test(const test&z)\n"); } test(test&& s)noexcept{ printf("test(test&& s)\n"); } test& operator=(test e) { printf("test& operator=(test e)\n"); return *this; } }; test Some_thing() { test i; return i; } int main() { Some_thing(); return 0; }</code>
此範例使用下列建構子按值傳回test 類型的物件:
當函式Some_thing被呼叫時,一個實例of test 預設在函式內部建立然後回傳。應用隱式移動規則,並使用移動建構子 test(test&&) 將臨時物件移到函數傳回的物件中。
因此,輸出顯示以下步驟:
範例:複製建構子
現在,讓我們考慮這個修改後的例如:
<code class="cpp">class test { public: test(int y) { printf("test(int y)\n"); } test() { printf("test()\n"); } test(test& z) { printf("test(test&z)\n"); } test& operator=(test e) { printf("test& operator=(test e)\n"); return *this; } }; test Some_thing() { test i; return i; } int main() { Some_thing(); return 0; }</code>
在這種情況下,移動建構函式test(test&&) 不可用。相反,複製建構子 test(test&) 用於將函數傳回的臨時物件複製到 main 中堆疊上建立的物件中。
輸出顯示以下步驟:
範例3:刪除建構函數
最後,如果我們明確刪除move像這樣的建構函數:
<code class="cpp">class test { public: test(test&& z) = delete; test(int y) { printf("test(int y)\n"); } test() { printf("test()\n"); } test(const test& z) { printf("test(test&z)\n"); } test& operator=(test e) { printf("test& operator=(test e)\n"); return *this; } }; test Some_thing() { test i; return i; } int main() { Some_thing(); return 0; }</code>
無法使用移動建構函數,編譯就會失敗,因為沒有可行的建構函數可用於傳回值。
總而言之,隱式移動當從物件是臨時的函數中按值傳回類別的物件時,將應用此規則。如果移動建構函式可用,則將使用它,如果沒有,則將使用複製建構函式。如果明確刪除移動建構函數,編譯將會失敗。
以上是當在 C 中按值傳回命名物件時,隱式移動規則是否適用?的詳細內容。更多資訊請關注PHP中文網其他相關文章!