c11右值引用 筆記

2022-07-15 19:42:11 字數 1574 閱讀 2700

c11中有左值引用和右值引用

對乙個變數的別名,不會呼叫拷貝構造,對別名的操作影響原值

執行結果:

對匿名變數的引用,提出右值引用的原因:充分利用在函式呼叫過程中產生的臨時變數,對這個臨時變數達到最大限度的使用率

常用的匿名變數(物件):

fun(a a());           //此時生產了乙個臨時變數,且無名,這就是右值

int  add(int a, int b)

return (a + b);   //此時的(a+b)的結果就是乙個臨時變數,且無名,這就是右值

並不是變數自動就會變成右值引用,需要使用者按右值引用的方式定義介面、定義變數,才會觸發右值引用,舉個例子:

1)fun (a a) { //再怎麼傳也不會變成右值引用

//todo

如果使用者使用  fun(a()); //則就是呼叫乙個普通的函式

2)如果想使用右值引用就需要使用者按右值引用定義介面,才會呼叫到這個右值引用

fun(a&& a){

//todo

fun(a());   //這時編譯器發現你有定義相關介面,就會去呼叫右值引用的函式了

上面1)和2)說的都是呼叫函式中的形參問題,下面說說變數問題;

int a=2, b=3;

int     c = add(a, b);         //c就是再普通不過的乙個左值,add先產生乙個臨時變數然//後再將臨時變數賦值給c

int&&  d = add(a, b);         //d就是乙個右值,add過程中產生乙個臨時變數,d就是這//個臨時變數的乙個「引用」,加引號是因為說d是乙個偷盜//者更合適,它把那個臨時變數給偷過來了

上面說的都是最正常的情況,即只對匿名變數(物件)使用右值引用,但是我們總是喜歡知道了乙個規則後,就千方百計利用這個規則,比如下面這種使用場景:

void test(){

t t;

fun(std::move(t));       //將t轉換成了乙個右值引用

void fun(t& t);    //左值引用

void fun(t&& t);  //右值引用

舉乙個可能用到的場景:

void print_(std::string&  str) {

std::cout

std::cout

std::string str(「hello world!」);

print_(str);                      //左值引用,後面str內容不變

print_(std::move(str));          //轉為右值引用 ,表示str可以被移動,但是否移動看後面介面的選擇了,由於此處僅是呼叫乙個接收右值引用傳遞的方法,

//並不會修改str,即並沒有進行move操作,所以呼叫完成後str內容不會發生改變

注意std::move的本質,它其實就是乙個轉換函式,將給定的型別轉化為右值引用,而並不是真正地「移動」了資源.

c 11 右值引用

右值引用 是一種復合型別,跟c 的傳統引用很類似。為更準確地區分兩種型別,我們把傳統的c 引用稱為 左值引用 而使用 引用 這一術語時,我們的意思同時包含兩種引用 左值引用和右值引用。右值引用的行為跟左值引用類似,不同之處在於 右值引用可以繫結到臨時量 右值 而 非const的 左值引用卻不能繫結到...

C 11 右值引用

消除兩個物件互動時不必要的物件拷貝,節省運算儲存資源,提高效率。能夠更簡潔明確地定義泛型函式。1.右值引用 int a a 1 here,a is an lvalue 上述的a就是乙個左值。c 11中左值的宣告符號為 為了和左值區分,右值的宣告符號為 printreference const str...

C 11右值引用

c 11中引入的乙個非常重要的概念就是右值引用。理解右值引用是學習 移動語義 move semantics 的基礎。而要理解右值引用,就必須先區分左值與右值。對左值和右值的乙個最常見的誤解是 等號左邊的就是左值,等號右邊的就是右值。左值和右值都是針對表示式而言的,左值是指表示式結束後依然存在的持久物...