青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

Benjamin

靜以修身,儉以養德,非澹薄無以明志,非寧靜無以致遠。
隨筆 - 398, 文章 - 0, 評論 - 196, 引用 - 0
數據加載中……

c++和closure(閉包)

一、定義: 是帶有上下文的函數。說白了,就是有狀態的函數。必須有上下文才能使用。
函數, 帶上了狀態, 就變成了閉包了. 什么叫 "帶上狀態" 呢? 意思是這個閉包有屬于自己的變量, 這些個變量的值是創建閉包的時候設置的, 并在調用閉包的時候, 可以訪問這些變量.
函數是代碼, 狀態是一組變量 ,將代碼和一組變量捆綁 (bind) , 就形成了閉包 ,內部包含 static 變量的函數, 不是閉包, 因為這個 static 變量不能捆綁. 你不能捆綁不同的 static 變量. 這個在編譯的時候已經確定了.
二、c++實現閉包的方法:
1、重載 operator() 例子
class MyFunctor { public: MyFunctor(float f) : round(f) {} int operator()(float f) { return f + round; } private: float round; }; float round = 0.5; MyFunctor f(round);

2、std::bind
int my_func(float f, float round) { return f + round; } float round = 0.5; std::function<int(float,float)> f = my_func;

3、lambda表達式,語法形式如下: [函數對象參數] (操作符重載函數參數) mutable或exception聲明 -> 返回值類型 { …函數體…}
[函數對象參數],例如[&,a,b]標識一個Lambda的開始,這部分必須存在,不能省略。函數對象參數是傳遞給編譯器自動生成的函數對象類的構造函數的。

函數對象參數有以下形式:
[ ] 空沒有使用任何函數對象參數。
[=] 函數體內可以使用Lambda所在作用范圍內所有可見的局部變量(包括Lambda所在類的this),并且是值傳遞方式(相當于編譯器自動為我們按值傳遞了所有局部變量)。
[&] 函數體內可以使用Lambda所在作用范圍內所有可見的局部變量(包括Lambda所在類的this),并且是引用傳遞方式(相當于編譯器自動為我們按引用傳遞了所有局部變量)。
[this] 函數體內可以使用Lambda所在類中的成員變量。
[a] 將a按值進行傳遞。按值進行傳遞時,函數體內不能修改傳遞進來的a的拷貝,因為默認情況下函數是const的。要修改傳遞進來的a的拷貝,可以添加mutable修飾符。
[&a] 將a按引用進行傳遞。
[a, &b] 將a按值進行傳遞,b按引用進行傳遞。
[=,&a, &b] 除a和b按引用進行傳遞外,其他參數都按值進行傳遞。
[&, a, b] 除a和b按值進行傳遞外,其他參數都按引用進行傳遞。

(操作符重載函數參數),例如(int a,int &b)標識重載的()操作符的參數,沒有參數時,這部分可以省略。參數可以通過按值(如:(a,b))和按引用(如:(&a,&b))兩種方式進行傳遞
mutable與exception聲明,例如 mutable throw(),可省略
按值傳遞函數對象參數時,加上mutable修飾符后,可以修改按值傳遞進來的拷貝(注意是能修改拷貝,而不是值本身,如果沒有添加mutable,相當于對函數參數的增加了const修飾,無法修改參數)。exception聲明用于指定函數拋出的異常,如拋出整數類型的異常,可以使用throw(int)。

示例:
->返回值類型,例如 ->int 表示返回 int類型
標識函數返回值的類型,當返回值為void,或者函數體中只有一處return的地方(此時編譯器可以自動推斷出返回值類型)時,這部分可以省略。
{函數體},例如{cout<<“abc”;},不可省略,可以為空

// 無函數對象參數,輸出:1 2   {    for_each(vctTemp.begin(), vctTemp.end(), [](int v){ cout << v << endl; });   }
   
// 以值方式傳遞作用域內所有可見的局部變量(包括this),輸出:11 12   {    int a = 10;    for_each(vctTemp.begin(), vctTemp.end(), [=](int v){ cout << v+a << endl; });   }   
 // 以引用方式傳遞作用域內所有可見的局部變量(包括this),輸出:11 13 12   {    int a = 10;    for_each(vctTemp.begin(), vctTemp.end(), [&](int v)mutable{ cout << v+a << endl; a++; });    cout << a << endl;   }   
 // 以值方式傳遞局部變量a,輸出:11 13 10   {    int a = 10;    for_each(vctTemp.begin(), vctTemp.end(), [a](int v)mutable{ cout << v+a << endl; a++; });    cout << a << endl;   }
   
// 以引用方式傳遞局部變量a,輸出:11 13 12   {    int a = 10;    for_each(vctTemp.begin(), vctTemp.end(), [&a](int v){ cout << v+a << endl; a++; });    cout << a << endl;   }   
 // 傳遞this,輸出:21 22   {    for_each(vctTemp.begin(), vctTemp.end(), [this](int v){ cout << v+m_nData << endl; });   }    
// 除b按引用傳遞外,其他均按值傳遞,輸出:11 12 17   {    int a = 10;    int b = 15;    for_each(vctTemp.begin(), vctTemp.end(), [=, &b](int v){ cout << v+a << endl; b++; });    cout << b << endl;   }

int temp = 10;
vector<int> ivec = {30, -10, -20, 50, 40 ,100, -50};
std::sort(ivec.begin(), ivec.end(), [](const int &x, const int &y) {return abs(x) < abs(y);});
std::for_each(ivec.begin(), ivec.end(), [&](int &x) { x += temp; cout << x << endl;});
三、注意事項:
比較上面三種方式,有一些細節需要注意:

1. closure的狀態特指其運行的上下文。 closure將存貯它運行時需要的上下文,從而保證在closure創建時的上下文可以在closure運行時依然有效。

比如round就是closure的上下文。保存上下文的這一特點通常被稱作“capture”或者是"bind"。 capture可以自己寫,比如MyFuctor f(round); 也可以用boost::bind。

當然最方便的還是讓編譯器幫你自動完成。編譯器將自動識別closure用到的變量,然后創建一個匿名的類,將這個變量保存到匿名類的成員變量中。

C++中有兩種capture方式,by value和by reference。寫法是[=]和[&]。

需要注意的是,capture by reference是不會修改被capture變量的生命周期的,你要保證被capture的變量在closure運行時是有效的。

這一點不像Java,Java中變量被capture的話,就變成被引用了,從而GC不會回收它。

2. closure的類型是隱藏的,每次創建一個closure,編譯器都會創建一個新的類型。

如果你想保存一個clousre時就不是那么直接,因為你不知道它的類型。這時那需要一些模板技巧,可參考boost::function的實現。

簡單的方式是直接用std::function來保存。

std::function<int(float)> closure;

closure = [](float f) { return 0.0f };

closure = [](float f) { return 1.0f };

四、閉包(匿名函數)用處,可以是流程更清晰,易于理解,一般不能單獨使用,必須有上下文,閉包里處理的是上下文中的一些變量。一般情況下不能單獨使用
auto Do=[&]()
{

}
auto nextDo=[=](){
}

posted on 2018-05-27 18:17 Benjamin 閱讀(836) 評論(0)  編輯 收藏 引用 所屬分類: C/C++

青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            激情91久久| 久久精品九九| 国产精品乱码妇女bbbb| 国产亚洲欧美一级| 欧美色网在线| 欧美视频网站| 欧美视频一区二区三区在线观看| 久久久91精品| 新狼窝色av性久久久久久| 国产主播一区二区三区四区| 国产一区二区精品久久99| 极品少妇一区二区三区精品视频| 国产婷婷一区二区| 最新高清无码专区| 亚洲视频你懂的| 久久成人一区| 免费观看在线综合色| 亚洲国产日韩欧美在线动漫| 美女主播一区| 亚洲一区在线播放| 看欧美日韩国产| 国产精品久久久久久久久久久久| 韩国一区二区三区在线观看| 日韩一二三在线视频播| 久久久综合视频| 一本色道久久综合亚洲二区三区| 欧美一级久久| 欧美日韩亚洲一区二| 亚洲第一毛片| 麻豆精品视频在线观看| 亚洲午夜久久久久久尤物 | 亚洲精品免费一区二区三区| 亚洲一区二区网站| 亚洲欧洲久久| 美女精品网站| 精品不卡一区二区三区| 亚洲综合不卡| 日韩午夜电影| 欧美激情亚洲激情| 亚洲黄色在线看| 蜜臀av一级做a爰片久久| 亚洲国产欧美久久| 久久综合久久综合久久| 欧美一区二区日韩| 国产一区二区丝袜高跟鞋图片| 中文久久乱码一区二区| 亚洲欧洲精品天堂一级| 欧美视频网址| 久久伊人一区二区| 免费成人在线观看视频| 亚洲精品久久久久中文字幕欢迎你| 欧美激情欧美狂野欧美精品| 欧美精品日韩精品| 欧美一区二区三区在线播放| 一区二区三区国产盗摄| 国产精品毛片a∨一区二区三区|国| 国产一区二区看久久| 久久女同互慰一区二区三区| 美国十次成人| 久久久青草青青国产亚洲免观| 久久精品国产精品亚洲精品| 亚洲日本成人| 欧美一区二区三区免费看 | 国产亚洲毛片| 欧美激情国产日韩| 国产欧美一区二区三区在线老狼| 亚洲第一在线| 国产在线欧美| 亚洲欧美日韩国产综合| 99热这里只有精品8| 久久久无码精品亚洲日韩按摩| 亚洲最新在线| 欧美日本国产视频| 老司机成人网| 亚洲肉体裸体xxxx137| 在线精品国精品国产尤物884a| 亚洲在线电影| 亚洲午夜一区二区三区| 欧美日本一道本| 亚洲激情精品| 极品日韩久久| 免费观看30秒视频久久| 欧美成年视频| 亚洲国产欧美一区| 欧美激情一区| 农村妇女精品| 国产一区二区日韩精品欧美精品| 99国产精品久久久久久久成人热| 亚洲精品视频一区| 欧美肉体xxxx裸体137大胆| 亚洲第一精品夜夜躁人人躁| 亚洲黄色成人| 国产精品久久久一本精品| 中日韩在线视频| 久久精品一区四区| 在线看一区二区| 欧美成年人视频| 亚洲永久免费视频| 欧美好骚综合网| 亚洲一区二区三区在线观看视频| 国产精品毛片高清在线完整版| 性久久久久久| 一本到12不卡视频在线dvd| 久久精品日韩| 亚洲视频自拍偷拍| 亚洲高清在线观看一区| 国产一区av在线| 国产精品九九久久久久久久| 欧美成人精品一区| 久久久精品久久久久| 亚洲欧美视频在线观看视频| 亚洲精品国产精品久久清纯直播| 国产精品videossex久久发布| 中国成人在线视频| 国产精品久久久久免费a∨| 欧美一区二区三区视频免费| 夜夜嗨av一区二区三区免费区| 美女免费视频一区| 久久综合色天天久久综合图片| 久久精品国产久精国产爱| 亚洲欧美在线x视频| 亚洲男人影院| 久久av免费一区| 久久五月婷婷丁香社区| 久久尤物视频| 亚洲精品综合久久中文字幕| 亚洲国产一区二区精品专区| 亚洲国产专区校园欧美| 亚洲激情av| 欧美一二区视频| 免费在线成人av| 欧美日韩天天操| 国产在线视频欧美| 日韩一级网站| 免费亚洲电影| 亚洲在线视频一区| 欧美成人精品h版在线观看| 欧美日韩你懂的| 一区二区三区在线免费观看| 一区二区欧美亚洲| 欧美成人精品在线观看| 一区二区三区欧美激情| 久久久久久久久久久成人| 欧美精品久久久久久久久久| 国产一区二区三区久久精品| 9色精品在线| 欧美激情一区二区三区成人| 亚洲欧美一区二区三区久久| 欧美日韩视频免费播放| 999亚洲国产精| 久久成人免费| 一区二区三区欧美视频| 美女福利精品视频| 亚洲日本精品国产第一区| 国产精品欧美日韩久久| 亚洲精品中文字幕在线观看| 欧美jizz19性欧美| 久久精品一区蜜桃臀影院| 国产精品家教| 性欧美长视频| 欧美在线亚洲一区| 一区在线视频| 亚洲国产三级网| 欧美四级伦理在线| 欧美在线播放| 美日韩精品免费观看视频| 亚洲精品日日夜夜| 亚洲嫩草精品久久| 激情婷婷亚洲| 日韩一区二区精品视频| 黄色成人在线| 欧美福利一区二区三区| 欧美视频在线观看免费| 久久人人爽人人爽爽久久| 欧美高清日韩| 久久aⅴ国产欧美74aaa| 欧美成人dvd在线视频| 亚洲制服丝袜在线| 美女视频黄 久久| 先锋影音久久久| 欧美成年网站| 亚洲福利视频在线| 在线免费精品视频| 亚洲韩国青草视频| 老鸭窝毛片一区二区三区| 亚洲视频www| 欧美国产一区二区| 美女日韩欧美| 国内精品视频666| 欧美亚洲综合网| 久久国产精品一区二区三区| 欧美精品xxxxbbbb| 亚洲国产女人aaa毛片在线| 欧美日韩免费精品| 一区二区电影免费在线观看| 在线播放日韩专区| 性感少妇一区| 美脚丝袜一区二区三区在线观看| 国产精品福利网| 亚洲日本一区二区三区|