15、lambda表達式、右值引用、移動語義

前言

返回值后置

auto 函數名 (形參表) ->decltype(表達式)

lambda表達式

lambda表達式的名稱是一個表達式 (外觀類似函數),但本質絕非如此

語法規則

[捕獲表] (參數表) 選項 -> 返回類型
{
函數體;
}

lambda表達式的本質

  • lambda表達式本質其實是一個類
  • 并且最終返回值為這個類的對象
  • 因此對lambda表達式的調用就是該對象的函數操作符的調用

簡寫

  • 可以沒有返回值類型,將根據return推斷
  • 如果連return也沒有,則返回值為void
  • 參數為void可以省略不寫

捕獲表

  • []:不捕獲任何外部變量
  • [variable] : 捕獲外部變量的值(具備只讀屬性)
  • [&variable]: 按引用捕獲,指定的外部變量
  • [this]: 捕獲this指針,訪問外部對象的成員
  • [=]: 按值捕獲所有的外部變量,也包括this
  • [&]: 按引用捕獲所有的外部變量,也包括this
  • [=,&variable]: 按值捕獲所有的外部變量包括this,但是指定的外部變量按引用捕獲
  • [&,=variable]: 按引用捕獲所有的外部變量,也包括 this,但是指定的外部變量按值捕獲
// lambda表達式
#include <iostream>
#include <typeinfo>
using namespace std;int Max(int x, int y){return x > y ? x : y;
}int main( void ){int a = 10, b = 20;cout << Max(a,b) << endl;;auto f = [](int x, int y)->int{ return x > y ?  x : y; };// 編譯器根據lambda表達式(1)生成一個類 (2)類內定義函數操作符函數 (3)返回這個類的匿名對象/*class Z4mainEUliiE_{public:int operator()(int x, int y){return x > y ?  x : y;}};auto f = Z4mainEUliiE_{};*/cout << "f的類型:" << typeid(f).name() << endl;cout << f(a,b) << endl; // f.operator()(a,b)// lambda表達式可以沒有返回值類型,根據return判斷cout << [](int x, int y) { return x+y; }(a,b) << endl;/*class X{public:auto operator()(int x, int y)->decltype(x+y){return x + y;}};cout << X{}(a,b) << endl; // cout << X{}.operator()(a,b) << endl;*/ // lambda表達式可以沒有返回類型,也沒有retrun語句,返回類型為void[](int x, int y){ cout << x << ' ' << y << endl; }(a,b);/*class XX{public:void operator()(int x, int y){cout << x << ' ' << y << endl;}};XX{}(a,b); // XX{}.operator()(a,b)*/// 如果沒有形參,可以省略不寫[]{ cout << "無聊" << endl;}();/*class XXXX{public:void operator(){cout << "無聊" << endl;} };XXXX{}();  // XXXX().operator()()*/ return 0; 
} 
// lambda表達式 -- 捕獲表(捕獲lambda表達式外部的變量信息)
#include <iostream>
#include <typeinfo>
using namespace std;int a = 10;class Y{
public:void foo(/* Y* this */ int c = 30 ){cout << "-------------[]----------------" << endl;[](int d = 40){cout << "a=" << a << endl;cout << "b=" << b << endl;
//          cout << "c=" << c << endl; // errorcout << "d=" << d << endl;
//          cout << "e=" << e << endl; // error}();/*class X{public:void operator()(int d = 40)){cout << "a=" << a << endl;cout << "b=" << b << endl;//  cout << "c=" << c << endl; // errorcout << "d=" << d << endl;//  cout << "e=" << this->e << endl; // error}};X{}();*/cout << "-------------[c]----------------" << endl;// 捕獲外部變量的值[c](int d = 40){ cout << "c=" << /*++*/c << endl; }();/* class XX{public:XX(int m):c(m){} //這里的c并不是foo函數的形參,而是XX類的一個成員變量void operator()(int d = 40){ cout << "c=" << c << endl; // //這里的c并不是foo函數的形參,而是XX類的一個成員變量}private:const int c; //這里的c并不是foo函數的形參,而是XX類的一個成員變量};XX{c}(); // 這里的c是foo函數的形參c   XX(c).operator()()*/cout << "-------------[&c]----------------" << endl;[&c](int d = 40){ cout << "c=" << ++c << endl; }();cout << "-------------[&c]----------------" << endl;[this](int d = 40){ cout << "e=" << e << endl; }();}private:static int b;int e;
};int Y::b = 20;int main( void ){Y y;y.foo();return 0; 
} 

右值引用

左值 和 右值

  • 可以“取”地址的值就是左值,左值通常具名
  • 不可“取”地址的值就是右值,右值通常匿名
    在這里插入圖片描述

左值引用 和 右值引用

  • 左值引用只能引用左值,不能引用右值
int a;
int& b = a; // OK
int c;
int& d = a + c; // ERROR
  • 右值引用只能引用右值,不能引用左值
int&& e = a + c;// OK
int&& f = a; // ERROR
  • 常左值引用,既能引用左值,也能引用右值
const int& g = a + c; // OK
const int& h = a; // OK

沒有必要有常右值引用,因為常右值引用,完全可以被常左值引用替代

// 左值/右值    左值引用/右值引用
#include <iostream>
using namespace std;int foo( ) {int m=888;return m;
}int main( void ) {
// 當前作用域的生命期
// 具名內存-->能夠取址-->左值|非常左值(無const修飾)
//                           |常左值  (有const修飾)int a = 10;int& ra = a; // okconst int& cra = a; // okconst int b = 10;
//  int& rb = b; // errorconst int& crb = b; // ok// 語句級生命期(引用可以延長右值的生命期)
// 匿名內存-->不能取址-->右值|直接更改右值毫無意義(98/03標準給出結論)
//                           | 11標準認為給了真名就可以改const int& ri = 10; int&& rri  = 10; const int& rf = /*|888|*/foo( ); // (1)分配一塊內存空間  (2)生成跳轉指令int&& rrf = foo();return 0;
}
//左值引用/右值引用
#include <iostream>
using namespace std;int main( void ) {int a,c;// 左值引用只能引用左值,不能引用右值int& b = a;  // ok
//  int& d = a + c; // error// 右值引用只能引用右值,不能引用左值int&& e = a + c; // oke = 666;         // ok 通過右值引用不會喪失修改目標內存的權限
//  int&& f = a;     // error// 常左值引用(萬能引用),既能引用左值,也能引用右值const int& g = a;     // okconst int& h = a + c; // ok
//  g = 666;  // error 但是通過常左值引用會喪失修改目標內存的權限return 0;
}

移動語義

資源的轉移 代替 資源的重建

保證功能正確的情況下,做到性能提升

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/213892.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/213892.shtml
英文地址,請注明出處:http://en.pswp.cn/news/213892.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

textarea文本框回車enter的時候自動提交表單,根據內容自動高度

切圖網近期一個bootstrap5仿chatgpt頁面的項目遇到的&#xff0c;textarea文本框回車enter的時候自動提交表單&#xff0c;根據內容自動高度&#xff0c;代碼如下&#xff0c;親測可用。 <textarea placeholder"Message ChatGPT…" name"" rows"&q…

TypeScript 第五節:條件語句

一、TypeScript 中常用的條件語句 TypeScript 的條件語句與 JavaScript 的條件語句類似&#xff0c;包括 if 語句、if...else 語句、switch 語句等。 1、if 語句 if 語句用于判斷指定條件是否為 true&#xff0c;如果是 true&#xff0c;則執行一段代碼塊。 示例&#xff1a;…

命名空間this_thread

命名空間 - this_thread 在C11中不僅添加了線程類&#xff0c;還添加了一個關于線程的命名空間std::this_thread&#xff0c;在這個命名空間中提供了四個公共的成員函數&#xff0c;通過這些成員函數就可以對當前線程進行相關的操作了。 1.get_id() 調用命名空間std::this_t…

java腳本引擎Groovy動態執行

1.java腳本引擎Groovy實戰_groovy腳本-CSDN博客 2.java可用的動態腳本引擎和動態代碼執行_java動態執行代碼片段-CSDN博客 3.Groovy動態加載Java代碼的使用方法和工具類_groovy調用java類方法-CSDN博客 4.springboot應用動態運行groovy腳本-附源碼 - 簡書 (jianshu.com) 5.…

是不是學了低代碼就自動放棄了高薪?內部資深解答來了!

目錄 前言低代碼開發&#xff1a;點餐還是自助烹飪&#xff1f;低代碼的“菜單”低代碼的局限性 市場影響的分析&#xff1a;一場關于低代碼的對話低代碼開發與程序員職業&#xff1a;名人視角解析總結 前言 近年來&#xff0c;低代碼開發因其低門檻、高效率和易集成的特點受到…

conda 計算當前包的個數

Conda是一個強大的包管理器和環境管理器&#xff0c;它用于安裝和管理來自不同源的軟件包。若要計算當前conda環境中安裝的包的數量&#xff0c;你可以使用以下命令&#xff1a; 首先&#xff0c;激活你想要檢查的conda環境&#xff08;如果不是默認的base環境&#xff09;&am…

虹科新聞丨廣州市“強企增效”項目助力虹科高質量發展!

來源&#xff1a;虹科電子科技有限公司 虹科新聞丨廣州市“強企增效”項目助力虹科高質量發展&#xff01; 原文鏈接&#xff1a;https://mp.weixin.qq.com/s/9pUXx5ZZpIi5S4s4o90GJA 歡迎關注虹科&#xff0c;為您提供最新資訊&#xff01; 2023年12月6日至7日&#xff0c;工…

hive/spark用法記錄

1. cast()更改數據類型 cast(column_name as type) 2. get_dt_date()自定義日期操作函數&#xff08;返回不帶橫線的日期&#xff09; select get_dt_date();–獲取當前日期&#xff0c;返回 20170209 select get_dt_date(get_date(-2));–獲取當前日期偏移&#xff0c;轉為…

如果將視頻轉化為gif格式圖

1.選擇視頻轉換GIF&#xff1a; 2.添加視頻文件&#xff1a; 3.點擊“開始”&#xff1a; 4.選擇設置&#xff0c;將格式選擇為1080P更加清晰&#xff1a; 5.輸出后的效果圖&#xff1a;

postgresql設置免密登錄

您提供的步驟描述了在 PostgreSQL 數據庫環境中配置服務器間的 SSH 無密碼登錄和數據庫用戶認證的過程。這些步驟主要用于設置一個高可用性、負載平衡的數據庫集群環境。讓我們逐一解釋這些步驟的目的和應用場景&#xff1a; 1. 啟動 PostgreSQL 服務 systemctl start postgr…

ReetrantReadWriteLock底層原理

文章目錄 一、讀寫鎖介紹二、ReentrantReadWriteLock底層原理1. 讀寫鎖的設計 一、讀寫鎖介紹 現實中有這樣一種場景:對共享資源有讀和寫的操作&#xff0c;且寫操作沒有讀操作那么頻繁(讀多寫少)。在沒有寫操作的時候&#xff0c;多個線程同時讀一個資源沒有任何問題&#xf…

jQuery-操作DOM

使用jQuery操作DOM dom : 文檔對象模型 就是HTML元素 $() 函數的2個用法: 用法1:放入一個字符串(選擇器)表示獲取元素 例如 $("p") $("#abc") $(".del") 用法2:放入一個函數&#xff0c;表示文檔就緒函數 例如 $(function(){代…

TikTok挑戰榜單:全球用戶如何共襄盛舉

TikTok作為全球最受歡迎的短視頻應用之一&#xff0c;在這個平臺上&#xff0c;用戶們通過參與各種挑戰&#xff0c;創造了無數令人驚嘆的短視頻。 本文將深入探討TikTok挑戰榜單的現象&#xff0c;探究全球用戶如何共襄盛舉&#xff0c;以及這種創意激發和社交互動如何成為Ti…

go-zero開發入門-API網關鑒權開發示例

本文是go-zero開發入門-API網關開發示例一文的延伸&#xff0c;繼續之前請先閱讀此文。 在項目根目錄下創建子目錄 middleware&#xff0c;在此目錄下創建文件 auth.go&#xff0c;內容如下&#xff1a; // 鑒權中間件 package middlewareimport ("context""e…

前端開發常用的Vscode插件整理(持續更新)

本文記錄用vscode進行前端開發時&#xff0c;常用到的有用的vscode插件&#xff0c;將不定時更新&#xff5e; 1、Chinese (Simplified) 將編輯器變成簡體中文 2、vscode-icon 讓 vscode 資源樹目錄加上圖標&#xff0c;官方出品的圖標庫 3、Import Cost 引入包大小計算,對于…

Springboot Redis Lua 分布式限流器

pom文件中添加如下依賴包&#xff0c;比較關鍵的就是 spring-boot-starter-data-redis 和 spring-boot-starter-aop。 <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-redis</artifactId></d…

基于ssm實驗室開放管理系統論文

摘 要 現代經濟快節奏發展以及不斷完善升級的信息化技術&#xff0c;讓傳統數據信息的管理升級為軟件存儲&#xff0c;歸納&#xff0c;集中處理數據信息的管理方式。本實驗室開放管理系統就是在這樣的大環境下誕生&#xff0c;其可以幫助管理者在短時間內處理完畢龐大的數據信…

高效純化樹脂A-2313 CPR

在化工、制藥等行業中&#xff0c;對colorful chemicals的純化一直是挑戰。本文將為您介紹一款具有卓越性能的強堿性陰離子交換樹脂——Tulsion A-2313 CPR。通過分析其特性和應用&#xff0c;展示其在colorful chemicals純化領域的優勢。 一、Tulsion A-2313 CPR離子交換樹脂的…

代碼隨想錄二刷 |二叉樹 |94.二叉樹的中序遍歷

代碼隨想錄二刷 &#xff5c;二叉樹 &#xff5c;二叉樹的中序遍歷 題目描述解題思路代碼實現迭代法遞歸法 題目描述 94.二叉樹的中序遍歷 給定一個二叉樹的根節點 root &#xff0c;返回 它的 中序 遍歷 。 示例 1&#xff1a; 輸入&#xff1a;root [1,null,2,3] 輸出&a…

漏洞復現-浙江宇視 isc LogReport.php 遠程命令執行漏洞(附漏洞檢測腳本)

免責聲明 文章中涉及的漏洞均已修復&#xff0c;敏感信息均已做打碼處理&#xff0c;文章僅做經驗分享用途&#xff0c;切勿當真&#xff0c;未授權的攻擊屬于非法行為&#xff01;文章中敏感信息均已做多層打馬處理。傳播、利用本文章所提供的信息而造成的任何直接或者間接的…