2011-04-03 78 views
2

如果我定義它接受一個rvalue參考參數的函數:右值參考參數和模板函數

template <typename T> 
void fooT(T &&x) {} 

我可以調用它,使用GCC 4.5,與任一aar,或arr

int a, &ar = a, &&arr = 7; 
fooT(a); fooT(ar); fooT(arr); 

但是,調用類似,非模板功能,

void fooInt(int &&x) {} 

這三個參數中的任何一個都會失敗。我正在準備加強我對forward的瞭解,但是這已經讓我失望了。也許它是GCC 4.5;我很驚訝地發現,從A Brief Introduction to Rvalue References第一個例子也給出了編譯錯誤:

A a; 
A&& a_ref2 = a; // an rvalue reference 
+0

使這個例子工作的正確方法是明確*使它成爲一個右值,其中:A && a_ref2 = std :: move(a)'。 *明確是一件好事,所以你不會意外移動東西。 – GManNickG 2011-04-03 21:22:28

+0

[Scott Meyers的解釋](http://channel9.msdn.com/Shows/Going+Deep/Cpp-and-Beyond-2012-Scott-Meyers-Universal-References-in-Cpp11)。這現在被稱爲*通用參考* – 2014-06-13 23:11:08

回答

9

扣除的行爲模板參數是獨特的,是什麼原因您的模板版本的作品。在另一個問題的背景下,我已經解釋了這種扣減的工作原理here

總結:當所述參數是一個左值,T被推斷爲T&,和T& &&塌陷到T&。並且在T&的參數下,向它提供左值T是完全有效的。否則,T仍爲T,參數爲T&&,它接受rvalues參數。

相反,int&&總是int&&(沒有模板推導規則強制它到別的東西),並且只能綁定到右值。

6

除了GMAN的正確答案A Brief Introduction to Rvalue References有一個不正確的例子,因爲它之前的語言改變其非法的寫:

A a; 
A&& a_ref2 = a; // an rvalue reference (DISALLOWED in C++11) 

儘管在語言的這種變化,主要使用(在文章中描述的情況移動和前進)仍然在文章中正確解釋。

更新:哦,和同一篇文章最初發布here與(imho)略好的格式。