欧美成人午夜精品久久久,国产?V天堂一区二区三区,欧美精品va在线观看,亚洲一区二区三区免费在线观看,av无码精品一区二区久久,欧美性爱视频不卡一区三区,欧美乱人伦视频在线观看,国产一级牲交高潮

ARTICLE DETAIL

資訊詳情

深耕商務建站與企業(yè)官網(wǎng)運營的一線實戰(zhàn)洞察。

C++11新特性實戰(zhàn):列表初始化、移動語義、lambda與function/bind

C++11新特性實戰(zhàn):列表初始化、移動語義、lambda與function/bind C11【第七篇】 ——— 列表初始化、移動語義、可變參數(shù)模板、lambda表達式、function包裝器和bind包裝器C11這批特性出來之后很多老代碼的回頭率真的低了不少。列表初始化、移動語義、可變參數(shù)模板、lambda、function、bind這幾個東西單獨拿出來每一個都能寫幾千字但日常開發(fā)里它們往往是一起出現(xiàn)的移動語義解決深層拷貝的痛lambda順手解決回調冗長的問題function和bind把各種可調用對象收編成統(tǒng)一類型可變參數(shù)模板在日志和工廠函數(shù)里直接省掉一坨重載。這篇作為C11系列第七篇默認你已經(jīng)有C98的使用基礎能看懂模板、類、左值右值的基本概念但對這批現(xiàn)代C特性還沒有系統(tǒng)梳理過。我會結合自己實際改代碼、寫庫、做框架時踩過的坑把每個語法的核心作用、底層邏輯和典型場景說透。1. 列表初始化C11給初始化方式立的規(guī)矩1.1 為什么一定要用花括號C98時代初始化方式散得離譜。數(shù)組有int arr[] {1,2,3};結構體可以Point p {1,2};單個變量既可以直接賦值int x 5;也可以用構造std::vectorint v(10);連指針初始化還分nullptr出來之前用NULL又是一堆坑。散亂意味著什么意味著代碼風格不統(tǒng)一意味著模板代碼想把任意類型初始化成一個值非常麻煩。C11給出的方案是統(tǒng)一花括號初始化列表初始化。不管是內置類型、數(shù)組、結構體、還是std::vector、std::map這種容器都可以用一對花括號把初始化列表寫清楚int x{ 5 }; int arr[]{ 1, 2, 3 }; Point p{ 1, 2 }; std::vectorint v{ 1, 2, 3, 4 }; std::mapstd::string, int m{ {a, 1}, {b, 2} };這個看似簡單的改動最大的意義在于讓初始化變成了“一種可以傳給模板和泛型代碼的語法結構”。我在寫泛型工廠時最直觀的感受就是以前要從一個參數(shù)列表去構造任意類型你得手寫一堆構造調用有了列表初始化和后面要講的可變參數(shù)模板一套代碼就能把任意類型任意參數(shù)的構造都接住這個收益是長期存在的。另外花括號初始化也在代碼風格上給出了極大的整潔度。團隊里只要規(guī)定“能用花括號初始化就盡量用”新老代碼的閱讀成本立刻下降這個對維護期的收益比很多人想象的大。1.2 initializer_list 與構造函數(shù)的“搶人大戰(zhàn)”花括號初始化背后依賴的核心類型是std::initializer_listT。當一個類定義了接受std::initializer_listT的構造函數(shù)時用花括號初始化它就會優(yōu)先走這條路徑class MyData { public: MyData(std::initializer_listint list) { std::cout initializer_list 構造, 元素數(shù)量 list.size() std::endl; } MyData(int a, int b) { std::cout (int, int) 構造 std::endl; } }; MyData d1{ 1, 2, 3 }; // 走 initializer_list MyData d2(1, 2); // 走 (int, int) MyData d3{ 1, 2 }; // 注意走 initializer_list 而不是 (int, int)這就是經(jīng)典坑點只要該類有 initializer_list 構造函數(shù)花括號初始化就優(yōu)先匹配它哪怕另一個普通構造函數(shù)匹配得“更精確”也不行。d3{1, 2}這種寫法很多人以為會走進(int, int)實際卻去了列表構造結果可能完全不一樣。這類問題在標準庫容器上表現(xiàn)得更加直接std::vectorint v1(10, 1); // 10個元素全部為1 std::vectorint v2{ 10, 1 }; // 2個元素分別是10和1v2這種寫法在代碼評審里經(jīng)常被年輕人拿來炫技但誤用也確實容易產(chǎn)生邏輯錯誤。生產(chǎn)環(huán)境下我更建議容器初始化明確的數(shù)據(jù)用花括號想要“填充n個值”這種語義就用圓括號別讓閱讀者猜。1.3 窄化轉換編譯期的安全檢查列表初始化另一個被低估的價值是禁止窄化轉換narrowing conversion。所謂窄化就是把一個高精度或大范圍的值隱式轉換成一個可能精度丟失或范圍縮小的類型。C98里這些都是默許的頂多出個警告但警告經(jīng)常被忽略double pi 3.14159; int a pi; // 編譯通過警告后靜默截斷 int b{ pi }; // 編譯錯誤double 到 int 是窄化轉換用花括號初始化時編譯器把這類轉換直接判為錯誤逼你顯式寫出意圖int b{ static_castint(pi) }; // 顯式轉換OK這個特性在維護大型項目時是個保護傘。我見過太多因為類型轉換丟精度產(chǎn)線上出事故的case罪魁禍首全是那些裸的隱式轉換?,F(xiàn)在不少現(xiàn)代代碼規(guī)范直接規(guī)定初始化必須用花括號顯式轉換必須用 static_cast兩者配合從源頭掐掉了一大批類型相關的隱蔽bug。唯一需要留意的是如果你在寫老代碼遷移一股腦全改成花括號初始化那編譯器會突然報出一堆“無法編譯”的錯這時候先別慌著用 static_cast 強行改回去要逐個確認那個窄化到底是有意還是無意往往能發(fā)現(xiàn)幾個之前被忽略的真實缺陷。2. 移動語義拷貝之外的第二條路2.1 右值引用到底在表達什么在C11之前左值右值的概念在語法層面只有“能不能取地址”這種粗糙的區(qū)分。C11引入右值引用之后我們可以寫一個專門接收“臨時對象”的接口臨時對象本質上是一個馬上要被銷毀的資源包這時再去深拷貝就是白白浪費性能。移動語義的精髓不是“快一點”而是“本來就不用復制”。右值引用理解上有個常見障礙它不是用來給變量“起一個右值的別名”的而是表示“這個東西是可以被掏空的臨時資源”。所以std::move的邏輯其實是把一個左值顯式地標注成“我允許你把它當臨時對象掏空”之后移動構造函數(shù)就會把資源指針直接拿過來把源對象置為空。class BigBuffer { public: BigBuffer(size_t size) : size_(size), data_(new char[size]) { memset(data_, 0, size); } // 拷貝構造深拷貝整塊內存 BigBuffer(const BigBuffer other) : size_(other.size_), data_(new char[other.size_]) { memcpy(data_, other.data_, size_); std::cout 拷貝構造被調用 std::endl; } // 移動構造直接接管指針 BigBuffer(BigBuffer other) noexcept : size_(other.size_), data_(other.data_) { other.data_ nullptr; other.size_ 0; std::cout 移動構造被調用 std::endl; } ~BigBuffer() { delete[] data_; } private: size_t size_; char* data_; };看這個BigBuffer的兩個構造拷貝構造要把整塊內存復制一份如果這塊內存是幾十MB一次深拷貝就是幾十MB的讀寫移動構造只是把指針從源對象手里拿過來再把源對象指針置空成本幾乎為零。這個差別在容器動態(tài)擴容、函數(shù)按值返回、中間臨時對象傳遞這些場景中是數(shù)量級的性能差異。2.2 移動賦值與“源對象被掏空”的紀律有移動構造自然就有移動賦值BigBuffer operator(BigBuffer other) noexcept { if (this ! other) { delete[] data_; data_ other.data_; size_ other.size_; other.data_ nullptr; other.size_ 0; } return *this; }注意這里必須先釋放自己原有的資源然后接管對方資源最后把對方置空。不釋放就接管會造成內存泄漏少了置空那一步則會導致源對象的析構函數(shù)把同一塊內存delete兩次直接觸發(fā)double-free問題。移動之后源對象處于“有效但未指定”的狀態(tài)標準要求它是可以安全析構、可以重新賦值的但你不能假設它里面還有原來的數(shù)據(jù)。我見過有人把std::move之后的源對象又拿去當普通變量用讀取到nullptr或者空字符串時一臉懵。所以誠實的做法是移動完一個對象后要么立即丟棄它要么明確把它重新初始化/賦值成可用的狀態(tài)。這里必須強調一個新手常見的幻覺移動語義并不是自動發(fā)生的它需要類本身定義移動構造函數(shù)/移動賦值。如果我們的BigBuffer只寫了拷貝構造沒有移動構造那么即使調用方把臨時對象std::move過來實際執(zhí)行的還是拷貝構造。很多性能敏感的代碼沒達到預期效果排查半天最后發(fā)現(xiàn)是類沒寫移動構造白白浪費了std::move的姿態(tài)。2.3 完美轉發(fā)std::forward 的正確用法模板編程中經(jīng)常遇到一個需求寫一個中間轉發(fā)函數(shù)把參數(shù)原樣轉給另一個函數(shù)并且要保留參數(shù)的左值/右值屬性——如果原來是左值繼續(xù)當左值傳過去如果是右值就保持右值屬性讓目標函數(shù)能夠移動它。這就是完美轉發(fā)。轉發(fā)引用也叫萬能引用的寫法是T它只在模板推導環(huán)境下成立templatetypename T void Relay(T arg) { // 這里如果直接傳 arg會丟失右值屬性 Process(std::forwardT(arg)); }std::forwardT的作用是根據(jù)T的推導類型來決定把arg轉換成左值還是右值。如果調用Relay時傳進來的是右值臨時對象T會被推導成某個具體類型forward就會把arg重新轉回右值引用讓下游能用移動語義接管它如果傳進來的是左值T推導成左值引用forward就原樣以左值傳遞。我在實現(xiàn)一些“軟件總線”式的中轉模塊時經(jīng)常用這個手法一個函數(shù)接收任意類型任意數(shù)量的參數(shù)然后轉發(fā)給真正處理請求的對象。不用完美轉發(fā)的話參數(shù)每經(jīng)過一層中轉都會損失類型信息臨時對象被迫退化成拷貝性能在多層轉發(fā)后會累積惡化。3. 可變參數(shù)模板編譯期的參數(shù)“打包”和“拆包”3.1 參數(shù)包怎么定義和展開可變參數(shù)模板讓函數(shù)和類可以接受任意數(shù)量、任意類型的參數(shù)。這在C98里只能靠重載或者va_list這種類型不安全的方式實現(xiàn)而在C11里參數(shù)的類型安全由編譯器保證。定義一個可變參數(shù)模板函數(shù)最基本的樣子templatetypename T void PrintOne(T value) { std::cout value std::endl; } templatetypename T, typename... Args void PrintMany(T first, Args... rest) { std::cout first ; PrintMany(rest...); }Args是一個模板參數(shù)包rest是一個函數(shù)參數(shù)包。rest...這個語法叫參數(shù)包展開把當前函數(shù)收到的剩余參數(shù)逐個展開再去調用下一層。整個遞歸過程會在參數(shù)包為空時落到那個單參數(shù)的重載上形成終止條件。很多初學者剛看到這個遞歸會覺得恐怖其實它就是編譯器在編譯期做了N層實例化每一層削掉一個參數(shù)直到削光。每個不同的參數(shù)組合都會生成一個獨立的函數(shù)實例所以如果調用方參數(shù)類型很多模板實例化數(shù)量也會增加編譯時間變長。但換來的是運行時的絕對高效——所有參數(shù)處理都發(fā)生在編譯期運行時沒有一個額外的分支判斷。sizeof...可以在不遞歸的情況下直接獲得參數(shù)個數(shù)templatetypename... Args void CountArgs(Args... args) { std::cout 模板參數(shù)個數(shù) sizeof...(Args) std::endl; std::cout 運行時參數(shù)個數(shù) sizeof...(args) std::endl; }這個操作符在遞歸展開前做數(shù)量判斷非常有用可以提前剪枝一些特化分支。3.2 遞歸展開最常見的套路可變參數(shù)模板最樸素的用法就是一個“處理一個剩下的交給下一層”的遞歸展開。上面打印的例子就是這樣的但實際項目中我更多用它做日志系統(tǒng)。比如寫一個能把任意類型任意數(shù)量參數(shù)拼進一條日志消息的工具class Logger { public: templatetypename... Args void Log(Args... args) { std::ostringstream oss; Append(oss, std::forwardArgs(args)...); WriteLine(oss.str()); } private: templatetypename T void Append(std::ostringstream oss, T value) { oss std::forwardT(value); } templatetypename T, typename... Args void Append(std::ostringstream oss, T first, Args... rest) { oss std::forwardT(first); Append(oss, std::forwardArgs(rest)...); } };這里我特意用了Args...轉發(fā)引用保證傳入的臨時字符串在拼日志時不會經(jīng)歷不必要的拷貝。日志系統(tǒng)往往處在高頻路徑上這類微小的性能優(yōu)化在實際壓測中是能看出來的。使用遞歸展開要注意一個細節(jié)遞歸調用必須用rest...把剩下的參數(shù)展開少寫一個省略號編譯器會立刻報錯“參數(shù)包必須至少展開到一個參數(shù)”。錯誤信息比較長新手容易慌其實核心就是檢查省略號位置。另外終止重載有條件是不能依賴運行時判斷的必須是編譯期的結構——要么用重載特化要么用if constexprC17的解決方案C11下比較穩(wěn)妥的辦法就是用重載或者偏特化來終止。3.3 逗號表達式展開不用遞歸的另一種方案遞歸展開思路清晰但每到N層參數(shù)就要實例化N個函數(shù)編譯時間會變成負擔。還有一種更緊湊的展開語法利用逗號表達式和初始化列表一次性把參數(shù)全部處理完templatetypename... Args void PrintAll(Args... args) { int dummy[] { (std::cout args, 0)... }; (void)dummy; }拆開看(std::cout args, 0)是一個逗號表達式——先執(zhí)行std::cout args再把0作為整個表達式的值。然后對這個表達式做參數(shù)包展開得到的實際是int dummy[] { (std::cout arg1, 0), (std::cout arg2, 0), ..., 0 };因為std::cout arg1返回的還是流對象不是int為了湊出數(shù)組元素類型為int用逗號表達式的0來兜底。這個技巧不必搞得花里胡哨但確實在一些空格分隔、不分層的場景比如把多個字符串直接拼進一個緩沖區(qū)里比遞歸更簡潔也省了一次次實例化遞歸殼子的開銷。我還見過一種變體是用std::initializer_listint{ (fun(args), 0)... }來展開效果類似。不管哪種寫法核心都是“用逗號表達式把真正的參數(shù)操作變成數(shù)組初始化表達式列表”這是C11時代沒有折疊表達式時的經(jīng)典套路。到C17之后折疊表達式(std::cout ... args)直接把這個場景簡化成一行但如果你的項目還鎖在C11標準這兩種展開方式就得熟練掌握。4. Lambda表達式就地定義一個匿名函數(shù)對象4.1 完整語法和默認行為lambda表達式提供了一種就地定義匿名函數(shù)對象的方式常見的完整語法長這樣[捕獲列表](參數(shù)列表) mutable - 返回類型 { 函數(shù)體 };最簡化形態(tài)甚至可以省略圓括號和返回類型比如auto f [] { std::cout hello std::endl; }; auto add [](int a, int b) { return a b; };返回類型在函數(shù)體只有一個return時一般可以靠auto推斷但如果函數(shù)體內多處返回不同類型的值或者類型比較復雜就需要顯式寫上尾置返回類型auto transform [](const std::string s) - int { return static_castint(s.size()); };關于mutable關鍵字有個容易混淆的點lambda的默認行為是捕獲列表里的值拷貝并且在lambda體內是只讀的。想修改拷貝進來的變量必須加mutableint count 0; auto counter [count]() mutable { return count; }; counter(); // 1 counter(); // 2 std::cout count; // 仍然是 0說明改的是lambda內部拷貝的值不加mutablecount這行會直接編譯報錯。很多人看到這個報錯第一反應是“是不是lambda不能修改外部變量”其實是忘了它是只讀語義。4.2 捕獲方式的選擇值、引用、混合捕獲捕獲列表是lambda的靈魂也是最容易產(chǎn)生生命周期bug的地方。幾種寫法各有適用場景[value]按值捕獲lambda內部持有外部變量的拷貝。[ref]按引用捕獲lambda內部持有的是外部變量的引用。[]默認按值捕獲所有使用到的變量。[]默認按引用捕獲所有使用到的變量。[, flag]混合捕獲flag用引用其余按值。按值捕獲看起來安全但要注意它拷貝的是“捕獲時刻”的變量快照。下面這段代碼是經(jīng)典陷阱std::functionvoid(int) funcs[5]; for (int i 0; i 5; i) { funcs[i] [i](int x) { return x i; }; // OKi按值捕獲每個lambda有自己的i快照 }如果把[i]寫成[]或者[i]那么所有l(wèi)ambda共享同一個i變量的引用循環(huán)結束后 i 的值是5所有l(wèi)ambda再執(zhí)行時拿到的都是5。這個錯誤在“循環(huán)里注冊回調”的場景中幾乎人人都會踩一腳而且非常隱蔽因為編譯毫無問題只有運行時行為不對。另一類生命周期問題是引用捕獲局部對象。比如有一個函數(shù)創(chuàng)建了一個局部對象然后返回一個捕獲了該對象引用的lambdastd::functionint() MakeFunctor() { int v 42; return [v]() { return v; }; // 引用懸空函數(shù)結束后v已銷毀 }這種代碼就是未定義行為。正確做法是按值捕獲[v]或者把局部對象放到堆上并用std::shared_ptr管理后讓lambda捕獲智能指針的拷貝。我在代碼評審中見過好幾例類似寫法全是抱著僥幸心理覺得“這個函數(shù)應該不會很快返回吧”結果程序運行一段時間后偶發(fā)亂值排錯成本遠超寫代碼成本。4.3 lambda在STL算法中的實戰(zhàn)lambda在C11里最大的用武之地是配合algorithm頭文件里的算法。以前寫std::sort要定義一個比較函數(shù)或者函數(shù)對象// C98風格 bool CmpDesc(int a, int b) { return a b; } std::sort(v.begin(), v.end(), CmpDesc);有了lambda之后std::sort(v.begin(), v.end(), [](int a, int b) { return a b; }); std::vectorint nums{ 5, 3, 8, 1, 9 }; int threshold 5; auto count std::count_if(nums.begin(), nums.end(), [threshold](int x) { return x threshold; });這種寫法把邏輯直接放到使用處既避免了“函數(shù)定義和使用地點分離導致的上下文割裂”又天然支持捕獲外部變量比函數(shù)對象寫起來緊湊得多。我習慣把lambda用在項目里的這些高頻場景做排序、查找、過濾的自定義謂詞作為事件回調、定時器的處理函數(shù)延遲執(zhí)行一小段邏輯比如保存到資源析構時才執(zhí)行的清理動作配合std::function做接口統(tǒng)一的策略回調。使用lambda時最好遵循一個原則lambda函數(shù)體不要寫太長。正常四五行的邏輯是最舒服的如果超過十幾行說明這段邏輯值得提取成一個具名函數(shù)或成員函數(shù)否則代碼的可讀性會因為“嵌套在一堆算法調用里的匿名邏輯”而急劇下降。5. function包裝器把可調用對象統(tǒng)一收納5.1 std::function 的使用與類型擦除std::function是一個通用多態(tài)函數(shù)包裝器它可以存儲、復制、調用任何可調用對象包括普通函數(shù)、函數(shù)指針、lambda表達式、函數(shù)對象以及用std::bind生成的綁定對象。它的核心價值在于用一個統(tǒng)一的類型去表示“具有特定簽名的可調用操作”。#include functional std::functionint(int, int) op; op [](int a, int b) { return a b; }; // lambda op [](int a, int b) { return a * b; }; // 換個lambda op std::multipliesint(); // 函數(shù)對象 op MyFunc; // 普通函數(shù)這個能力背后是類型擦除機制。簡單說std::function內部維護了一個抽象基類和一個具體的包裝類模板模板里面保存著原始可調用對象的副本同時實現(xiàn)了統(tǒng)一的調用接口operator()。外部只看到std::functionint(int,int)這樣一個明確的簽名不知道里面到底存的是函數(shù)指針、lambda還是函數(shù)對象。這個過程有點像“把所有形狀各異的插頭插到一個萬能插座上對外只暴露同一個三相插口”。在實際工程里std::function最大的意義在于把回調注冊、策略注入、事件分發(fā)這些場景的可調用對象類型全部統(tǒng)一了。比如一個按鈕的點擊事件回調你既可以注冊一個成員函數(shù)通過bind也可以注冊一個lambda外部存儲的都是std::functionvoid()。5.2 回調場景下的正確姿勢我重構過一些把裸函數(shù)指針作為回調參數(shù)的舊模塊最大的痛點就是函數(shù)指針無法捕獲狀態(tài)。你想傳一個“帶業(yè)務上下文”的回調只能通過void* user_data再傳一個裸指針各種生命周期隱患。有了std::function之后業(yè)務數(shù)據(jù)可以直接被lambda捕獲根本不需要void*這種極度不安全的通道。真實模塊里經(jīng)常是這樣的class EventDispatcher { public: using Handler std::functionvoid(const Event); void RegisterHandler(int eventType, Handler handler) { handlers_[eventType].push_back(std::move(handler)); } void Dispatch(int eventType, const Event evt) { auto it handlers_.find(eventType); if (it ! handlers_.end()) { for (auto h : it-second) { h(evt); } } } private: std::unordered_mapint, std::vectorHandler handlers_; };這個模式在各語言里都很常見C11以前要實現(xiàn)得費不少勁現(xiàn)在用std::function幾行搞定。注意我在RegisterHandler里用了std::move(handler)因為std::function內部保存的是可調用對象的副本這步能省一次深度拷貝。5.3 function 的性能與坑std::function性能上確實有開銷核心是間接調用和可能的堆分配。它內部存儲可調用對象的副本如果可調用對象小比如無捕獲的lambda等同于一個函數(shù)指針很多實現(xiàn)在棧上通過小對象優(yōu)化就直接存了但如果捕獲了大量狀態(tài)的lambda體積大就可能觸發(fā)動態(tài)內存分配。我在做高頻回調系統(tǒng)時實測過用裸函數(shù)指針一次間接調用幾納秒到幾十納秒std::function會有額外幾納秒到幾十納秒的開銷。在真正的熱路徑比如每幀幾十萬次回調上這個開銷會被放大這時要么換裸函數(shù)指針要么用更輕量的專用回調類型。另一個坑是拷貝std::function的開銷。std::function是可拷貝的但拷貝一個里面裝了很大lambda的std::function等于拷貝了那份捕獲狀態(tài)。所以函數(shù)傳參和注冊時優(yōu)先用const std::function...接收內部需要保存時再拷貝或std::move別動不動作值傳遞// 不推薦 void RegisterCallback(std::functionvoid() cb) { callbacks_.push_back(cb); // 至少一次拷貝 } // 推薦 void RegisterCallback(const std::functionvoid() cb) { callbacks_.push_back(cb); } // 或者右值版本 void RegisterCallback(std::functionvoid() cb) { callbacks_.push_back(std::move(cb)); }如果某個std::function永遠沒有被調用但它的捕獲對象很大那么這個對象就一直占著內存直到std::function被銷毀或重新賦值。一些長生命周期的事件表容易在不知不覺中累積大量捕獲上下文排查內存占用時記得檢查std::function的捕獲體量。6. bind包裝器把函數(shù)參數(shù)“提前預定”出新的可調用對象6.1 std::bind 的基本操作std::bind用來生成一個“綁定了一部分參數(shù)”的新可調用對象它把事情分成兩半一半在處理函數(shù)定義完之后就已知另一半留給真正調用時再傳。#include functional int Add(int a, int b) { return a b; } using namespace std::placeholders; auto add5 std::bind(Add, 5, _1); std::cout add5(3) std::endl; // 輸出8等價于 Add(5, 3) auto add5and10 std::bind(Add, 5, 10); std::cout add5and10() std::endl; // 輸出15參數(shù)全部綁定調用時無需傳參_1、_2這些是占位符表示“這個位置留給調用時傳入的第一個、第二個參數(shù)”。占位符放在第幾個位置就代表調用傳入的參數(shù)填到對應位置。利用這個機制還可以調整參數(shù)順序auto swapAdd std::bind(Add, _2, _1); std::cout swapAdd(3, 4) std::endl; // 等價于 Add(4, 3)輸出7這個“參數(shù)重排”能力在適配第三方接口時非常實用。比如一個消息處理器的回調簽名是void Handle(int msgType, int priority, const Message msg)而你的處理函數(shù)只關心 priority 不為0的消息并且你的處理函數(shù)簽名是void Process(const Message msg)可以直接auto binder std::bind(Processor::Process, processor, std::placeholders::_3); // 只取第3個參數(shù)傳給Process6.2 綁定成員函數(shù)和對引用的處理綁定成員函數(shù)是std::bind的高頻用法。成員函數(shù)隱含第一個參數(shù)是對象本身所以Processor::Process后面要么接對象指針要么接對象引用或拷貝Processor processor; auto binder std::bind(Processor::Process, processor, std::placeholders::_1); // 或者 auto binder2 std::bind(Processor::Process, processor, std::placeholders::_1); // 按值拷貝對象注意大對象拷貝開銷我個人的習慣是對象生命周期明確長于回調時用processor綁定不確定生命周期時優(yōu)先考慮std::shared_ptrProcessor的拷貝加std::bind的占位策略甚至直接改用lambda捕獲智能指針更直白。綁定引用參數(shù)時有個隱蔽坑std::bind默認按值保存綁定參數(shù)。如果函數(shù)參數(shù)是引用類型直接 bind 一個變量進去實際綁定的是它的拷貝函數(shù)內部改引用不會影響原變量。想要綁定真正的引用必須使用std::refvoid UpdateCount(int n) { n 10; } int count 0; auto binder std::bind(UpdateCount, count); // 按值綁定改了沒反應 auto binderRef std::bind(UpdateCount, std::ref(count)); // 綁定真實引用 binder(); binderRef(); std::cout count; // 輸出10binderRef那次修改生效了std::ref返回一個引用包裝器這是一個C11里看起來簡單但使用頻率不低的工具。凡是需要把引用“當值”傳遞的場景包括std::thread、std::bind、std::function的捕獲都必須靠它來表達引用語義。6.3 bind 和 lambda 該怎么選很多人糾結std::bind和lambda哪一個更好。我的結論非常直接C11項目里能用lambda的地方優(yōu)先用lambda只有在確實需要參數(shù)重排、或者一些極其簡單的綁定場景才考慮bind。原因有三方面。第一lambda語法更直觀可讀性更好[processor](int x){ processor.Process(x); }一眼能看懂捕獲了誰調用了誰而std::bind(Processor::Process, processor, _1)對不熟悉bind的人來說還要反應一下。第二lambda的捕獲是顯式的[]、[]、[a]而bind是隱式按值保存在內部包裝對象里排查生命周期問題時lambda更直觀。第三編譯器對普通lambda的優(yōu)化能力比對std::bind生成的復雜包裝對象更強內聯(lián)概率更高。但 bind 并不是完全沒有價值。在某些需要真正“參數(shù)重排”的適配場景或者早期C11代碼風格已經(jīng)在團隊里形成慣例的項目里bind依然是可讀的。而且std::bind和std::function配合得相當自然std::functionvoid(int) callback std::bind(Processor::Process, processor, _1);在C14、C17之后泛型lambda和更高階特性的引入讓 bind 的使用場景更少了但如果你的項目還被鎖在C11標準bind 仍然是所有標準庫容器和類接口里的“一等公民”該會還得會。7. 常見問題與排查技巧實錄實際代碼中把這些特性組合使用踩坑的概率并不低。我把這幾年見過的高頻問題整理成一組速查方便大家對照。問題現(xiàn)象根本原因排查思路與修復花括號初始化導致窄化編譯錯誤int x{doubleVal}被禁止窄化顯式static_castint或者改用圓括號初始化如果確實需要舊行為深拷貝意外發(fā)生性能突然下降類沒有定義移動構造/移動賦值或者傳參時忘了std::move檢查類是否有noexcept移動構造檢查熱路徑上的拷貝調用循環(huán)內注冊的lambda回調值全部相同引用捕獲了循環(huán)變量變量最終是同一個終值改按值捕獲[i]或拷貝一份局部臨時變量再捕獲lambda按引用捕獲的對象已銷毀局部變量生命周期結束引用懸空按值捕獲或者把對象生命周期延長到堆上并用智能指針接管可變參數(shù)模板遞歸沒有終止重載缺少單參數(shù)版或者特化像PrintMany例子那樣補一個templatetypename T void Print(T)作為終止std::bind綁定引用參數(shù)但外部值不改變bind默認按值保存參數(shù)用std::ref顯式包裝引用std::function頻繁拷貝導致卡頓大捕獲狀態(tài)的function被反復按值傳遞函數(shù)參數(shù)用const std::function...接收存儲時std::move7.1 初始化相關的坑列表初始化最大的兩個坑是窄化轉換和initializer_list的優(yōu)先級。窄化轉換編譯錯誤一般不難定位關鍵是要定好項目規(guī)范在需要強制類型安全的代碼路徑上統(tǒng)一用花括號初始化。initializer_list的優(yōu)先級問題則更難防我的經(jīng)驗是凡是定義了initializer_list構造函數(shù)的類在代碼評審時要特意檢查所有{}初始化的位置確認確實是想走列表構造而不是普通構造。標準庫里std::vector、std::map、std::list都有這種行為稍不留神就會把“構造10個元素”寫成“構造1個元素內容為10”。7.2 lambda捕獲引發(fā)的懸空引用lambda捕獲問題的根源是生命周期管理。值捕獲雖然安全但也有代價捕獲了超大對象的lambda一旦存入std::function那個對象就一直被持有到function銷毀。如果這個function被存進全局容器那就是隱形的內存占用。我在實現(xiàn)定時任務系統(tǒng)時遇到過一個案例定時器回調捕獲了一個幾十MB的配置對象結果這個定時器對象一直存放在調度表里幾十MB內存被白白占著。后來改成捕獲std::shared_ptrConfig的拷貝并且在回調完成時從調度表移除問題才解除。7.3 可變參數(shù)模板遞歸不終止遞歸展開的模板如果不加終止條件編譯器會無限遞歸實例化下去最終報錯信息里會出現(xiàn)recursively required from 函數(shù)名...展開的模板list一長串看得人頭皮發(fā)麻。排查方法很簡單從報錯信息里找到最內層那個沒有終止重載的調用點補上單參數(shù)版本或者空參數(shù)版本即可。另一種不易察覺的問題是遞歸展開的每一次實例化都會在二進制里產(chǎn)生一個真實存在的函數(shù)符號參數(shù)多、調用頻繁時二進制膨脹和編譯時間上漲都能感覺到。如果對編譯期性能敏感盡快考慮C17的折疊表達式或者C11下的逗號表達式展開方案。7.4 移動語義相關坑移動之后的源對象問題我在代碼評審時看到過的錯誤包括移動后直接使用源對象的成員沒檢查空指針、移動賦值之前沒有釋放原資源造成泄漏、移動構造函數(shù)忘了noexcept導致 vector 擴容時退化為拷貝、以及無代價地把一個左值std::move進一個馬上還要用的地方。針對這些比較實際的規(guī)約是移動構造函數(shù)和移動賦值必須標注noexcept否則標準庫容器擴容時可能會改用拷貝而不是移動性能收益直接歸零。移動后的源對象要約定“視為懸空”除了重新賦值和析構不要讀它的成員。std::move不是“強制搬移”它只是把左值標記成“可供搬移”。最終是否搬移取決于目標類型有沒有移動構造/移動賦值。7.5 function/bind的坑std::bind與std::function組合的坑通常出現(xiàn)在捕獲生命周期上。由于 bind 在存儲被綁定參數(shù)時默認按值因此如果你在函數(shù)里 bind 了一個局部變量并把這個綁定器存到全局局部變量雖然已經(jīng)銷毀但 bind 內部保存的副本還在——這其實是安全的。真正不安全的是綁定了一個std::ref(localVar)因為那保存的是真實引用如果局部變量沒了引用就懸空。這種懸空與lambda引用捕獲懸空是同一個本質問題。排查引用懸空類bug時優(yōu)先懷疑兩處lambda的[]/[var]捕獲以及 bind 里的std::ref。另外一個容易被忽略的點是std::function的賦值與默認狀態(tài)。未賦值的std::function是空的調用它時拋std::bad_function_call。在多線程回調注冊場景里先判斷if (handler)再做調用是必要的防御但真正安全的長效方案是在回調注冊/注銷時加鎖管理避免同一個handler在執(zhí)行中被另一個線程替換或清空。8. 個人經(jīng)驗這幾個特性組合起來才是真香單獨看列表初始化、移動語義、可變參數(shù)模板、lambda、function、bind每個都是“獨立的新語法”但在實際工程里它們經(jīng)常是擰在一起用的。我在寫一個輕量級的消息總線模塊時這種合力體現(xiàn)得最明顯消息總線的注冊接口需要支持各種類型的事件處理器。事件處理器的類型不一樣有的是普通函數(shù)有的是成員函數(shù)有的是lambda怎么辦用std::function統(tǒng)一存儲配合bind把成員函數(shù)轉成std::function配合lambda捕獲業(yè)務上下文。事件對象的構造用列表初始化加可變參數(shù)模板一條消息的參數(shù)可以全部打包進一個對象。消息發(fā)送時用移動語義把消息對象直接交給下一個模塊避免大數(shù)據(jù)拷貝。整套代碼下來比起以前C98的實現(xiàn)既簡短又清晰性能還更好。如果非要說一個最值得優(yōu)先掌握的組合我建議把“l(fā)ambda std::function 移動語義”這組先練熟。它們能覆蓋日常80%的回調與策略場景而且思考方式可以遷移到C14、C17甚至C20的后續(xù)特性上??勺儏?shù)模板和完美轉發(fā)屬于模板庫作者級能力學習曲線稍微陡一點但理解了“編譯期參數(shù)打包/拆包”這個模型之后再去看std::tuple、std::make_unique這些標準庫實現(xiàn)的源碼會有豁然開朗的感覺。我自己的經(jīng)驗里還有一個很實際的小技巧在調試模板相關的問題時編譯錯誤信息通常特別長千萬別從上往下掃直接翻到最底部的note:或者error:那一行往往才是真正的錯誤源頭。配合這些新特性時代碼風格上建議定義一套固定寫法初始化盡量用花括號移動構造/移動賦值寫noexceptlambda捕獲值顯式寫出function作為回調類型統(tǒng)一用別名。時間久了你會發(fā)現(xiàn)這批特性不光是語法糖它們確實讓C代碼寫起來更接近“描述意圖”而不是“描述每一步操作”這也是C11最大的價值所在。
返回列表
PREV
查看更多資訊
NEXT
返回資訊列表
久久综合五月天| 婷婷五月色惰| 激情综合网激情五月俺也去| 婷婷视频在线| 开心久久网婷婷| wwccc久久久| 婷婷五月天av| 久久久久思思热| 三十熟女| 婷婷狠狠干| AV免费在线网站| 91人人澡人人爽人人看| 99热啪啪| 六月香五月婷| 大香蕉久久久久久久久| 丁香花五月天激情| 久久久久久久久久久久久久人妻视频| 婷婷五月天天| 99久在线精品99re5热视频| 婷婷久久18| 无码色| 大香蕉人在线65| 色五月五月天色婷婷色五月| 亚洲色9| 97久久超碰| 91九色在线| 九热视频| 激情5月婷婷| 色色色地址| 九九伊人网| 丁香六月亚洲| 97在线日本| 大香蕉伊人99| 久久只这里有精品| 小泽玛利亚视频一区二区| 久久久久久久五月婷婷六月丁香综合,开心激情综合网 | 激情五月婷婷| 丁香五月五月婷婷| 色丁香婷婷| 日本三级中国三级99人妇网站| 欧美综合激情五月| av国产精品偷| 亚洲综合1024| 六月亭亭久久综合激情| 九九狠狠干| 天天干夜晚夜操| 婷婷五月天六月综合| 91碰免费视频| 99热色精品| 六月丁香综合网| 激情熟女网| 色综合99| 日日撸夜夜操| 日韩无码人妻一区二区三区综合| 26uuu丁香婷婷五月| 天天干电影| 五月草影视| 99视频在线播放大全| 亚洲综合网激情五月天| 丁香熟女乱| 亚洲1区| 日本性激情色播| 色五月,婷婷大香蕉| 97久久久| 五月天激情国产综合婷婷| 成人AV免费观看| 精品香蕉99久久久久网站 | 久久久久久久11111111111| 99爱在线免费视频| 99色热综合| 丁香狠狠色婷婷| 亚洲国产精品VA在线看黑人| 婷婷在线视频| 色99色| 中文字幕黄色片| 婷婷五月欧美综合| 亚洲天堂热| 色五月激情五月开心五月| 91人操| 高潮毛片又色又爽免费| 91在线日| 人妻久久久久久久久久久| 伊人网欧美在线男人天堂五月丁香| 一级黄色片看看| 久久XX| 亚艹艹| 六月丁香啪| 九月丁香八月婷婷久久综合久97| 99热手机在线精品| 色色色婷婷五月天| 国产亚洲精品久久一区二区三区| 综合五月丁香六月婷婷| 五月色导航| 五月婷婷在线观看黄| 三级大香蕉网| 丁香五月激情鲁| 丁香婷婷影院| 啊v视频在线观看| 国产真实乱了老女人视频| 99久久户外勾搭| 日韩野外 无套| 国产精品 的国产| 五月婷婷免费在线| 天天天操天天天日| 久久久五月天| 天天操天天曰天天射| 久久99久久99精品免观看粉嫩| 六月丁香啪啪| 五月天堂在线| 婷婷五月天激情小说| 91紱請| www.金莲av| 99热这里只有免费精品| 久热婷婷| 九热...av| 国产色丁香| 噜噜噜精品欧美成人在线观看| 天天操婷婷| 99热这里只有精品1025| 色偷偷五月天| 婷婷色色丁香五月天| www.色婷婷| 91嫩草国产线观看亚洲一区二区| 亚洲操操| 日韩黄色电影| 五月婷婷激情在线| mmm1717.6dbm人人爱人人操| 五月丁香操婷逼| 亚洲精品又粗又大又爽A片| 这里只有精品96| 婷婷五月花| 天天五月情| 成人精品在线观看| 丁香五月婷婷综合激情啪啪啪啪啪啪啪| 手机在线日韩视频中文字幕| 天天干 夜夜爽| 99热亚洲| 丁香五月婷婷深爱综合激情| 91色吧网| 丁香激情五月少妇| 五月天影院| 色激情五月| 综合久久8| 五月婷婷激情综合在线| 亚洲另类视频| 亚洲日本韩国| 青青草a在线| 久狠狠| 久久精品一区二区三区四区| 99在线精品视频观看免费下载| 色五月aV| 天堂草在线看www| 五月丁香色婷| 久久机热/这里只有精品| 综合久久人妻| 五月婷婷在线视频观看| 久在线88综合| 激情综合啪啪| 激情五月瑟瑟| 丁香五月视频在线观看| 色五月综合| www.婷婷五月天| 久久久久思思热| 日日躁夜夜躁狠狠久久AV| 五月丁香啪啪啪啪| 996日日爱| 五月综合缴情网| 99热6色| 五月天综合色| 超碰在线91| 九九操屄| 综合久久高清| 无码G高清天| 天天摸天天日天天舔| 激情五月天婷婷在线网址发给我| 直接看的av| 亚洲蜜桃精久久久久久久久久久久| 超碰无码老师| 五月丁香婷婷福利| 五月婷婷中文字幕| 五月婷婷啪啪| 国产免费av网站| 国产激情在线| 国产精品色色色色| 色婷婷大香蕉| 99视频热99| 99综合自拍| 成人五月天婷婷| 婷婷射图五月天| 欧美草久久五月天91| 97操碰在线视频| 天天爱天天做天天操| 亚洲午夜成人av电影网| 九热...av| 天天射射夜| 婷婷五月六| 十一月婷婷激情四射| 精品久久久人妻| AⅤ网站在线看| 九九精彩久久| 骚货艹网站视频| 天天干天天干天天干天天干天天干| 激情五月天小说|五月天开心激情网|亚洲精品国产自在现线|黄色五月天 | 97爱综合| 六月丁香五月激情网| 成人丁香五月天Av| 伊人九热| 丁香六月 人妻| www.色婷婷| 国产精品扒开腿做爽爽爽A片唱戏| 色色丁香色五月| 播五月婷婷开心| 色色色综合色| 丁香狠狠干| 婷婷的久久网站| 午夜电影网VA内射| 五月天激情小说| 丁香五月婷婷免费视频| 五月婷丁香花| 久婷婷婷| 欧美婷婷九月| 甈吧vv| 日本一道久久| 狠狠爱婷婷丁香| 九九婷婷五月天影视| AV在线免费播放| 一本婷婷丁香久久| 午夜性爱影视一区77| 婷婷性爱网| 人妻激情网| 另类婷婷丁香| 九九在线视频| 欧美群妇大交乱婬网| 五月婷婷五月色| 激情操逼婷婷| 99色播| www激情| www.色九月| 天天爽夜夜爽夜爽精品| 情欲禁地| 五月婷色色| 久久久这里有精品| 69久热| 五月丁香好婷婷A片网| 久热99| 97色色综合| 五月婷婷久草在线视频综合| 丁香婷婷狠狠97| 就是色婷婷五月亚洲色| 男女99免费视频| g00d人体西西| 丁香五月欧美| 9精品视频在线| 久久久人妻人伦| 欧美99视频| 日本97在线看片| 六月婷婷影院| 婷婷香蕉香| 热久久视频99| 久久xx| 色~性~乱~伦~噜| 天天色综网| 涩丁香| 亚洲天堂AAA| 99热伊人| 美女要搞搞天天搞搞搞网站| 香蕉久久av一区二区三区| 五月丁香在线视频观看| 五月综合激情网| 色五月成人婷婷| 天天色视频| 99天堂网| 国产毛片精品一区二区色欲黄A片| 五月天色图| 色色五月丁香婷婷| 五月丁香网av| 国产精品天天狠天天看| 色欲丁香久久| 182tv992tv人之初午夜免费观看| 五月丁香六月婷婷综合| 国产精品国产| 丁香五月六月婷婷综合| 97干在线看| 色色色色综合| 91se在线视频| 人人操五月天| 色热久资源| 五月丁香亭亭| 亚洲色色爱| 亚洲精品色| 久久久区区一久久久久久| 五月丁小婷婷激情四射| 天天插天天干| 天天色天天搡| 中国操逼99| 操啊操av| 日本婷婷在线| 五月丁香婷婷在线| 五月天成人在线视频丁香| 亚洲日韩一页精品发布| 深情五月天| 色七七九九| 播播网色播播| 狠色狠色狠狠色综合网| 五月色亭丁香| 99天堂网| 青草性爱视频| 夜夜嗨一区二区三区直播内容| 久久机热思思热| 五月日韩中文字幕| 日熟女| 色婷婷激情视频| 九九这里有精品| 婷婷的99视频网站| 超碰日韩人妻在线| 亚洲AV日韩无码| 婷婷五月天激情文学小说| 亚洲乱码日产精品BD| 天天爽日日爽夜夜爽| 五月丁香色婷婷色| 婷婷五月天AV| 色 五月婷婷基地| 婷婷久久图片| 国产精品色| 丁香六月色婷婷| 五月丁香精品| 欧美经典片免费观看大全| 丁香色情五月综合网站| 东京热伊人| 无码激情AAAAA片-区区| 另类激情五月| 99日这里只有精品| 丁香婷婷精品视频| 99啪在线视频| 97亚洲视频在线| 色婷婷视频在线| 五月天大香蕉| 色婷亚洲| 欧美 色婷婷| 97视频久久| 99视频精品8| 手机旧版看人妻1025| 人妻人人操| 热99只有精品| 狠狠看狠狠| 久久婷婷桃花五月天| 开心五月深爱五月| 色色无码| 五月天激情美女久久| 久热综合| 久久中国毛毛片爱久久| 久久人妻少妇嫩草AV| 国产婷婷五月色情综合| 婷婷丁香五月精品| 久久久久妻| 香蕉中文在线| 99久久超级| 五月久久婷婷天堂视频| 五月色色激情网| 99热思思在线观看| 国产99热| 91色综合网| 六月婷婷天堂| 日本三级成人秘书精品片| 九九热99视频| 婷婷激情五月综合| 亚洲国产成人裸舞| 日本www五月婷婷| 五月丁香啪啪综合| 五月丁香毛片| 二区成人视频| 色综合激情图区| 色婷久久| 九九99久久| 丁香美女五月天婷婷| 激情五月天网页| 超碰99在线| 99五月婷| 97丁香五月| 就爱日五月天| 123日本不卡在线| 婷婷五月天成人网| 99热思思| 日日噜噜夜夜狠狠久久丁香六月| 激情性爱五月天| 丁香五月婷婷五月天| 停停五月天激情网 | 激情五月综合亚洲另类| 99精品网| 99热精品在线在线| 欧美色性色好| 婷婷成人五月天成人文学| WWW.色婷婷.COM| 99热这只有| 一区色色色色网| 欧美日韩成人高清在线| 影音先锋 一区| 五月天婷婷无码| 五月日韩中文字幕| 婷婷欠久少妇| 久综合九综合99| 久久综合九色综合97婷婷| 疯狂做受XXXX高潮A片| 丁香五月色| 欧美日韩91| 激情婷婷色色| 丁香五月六月综合激情| 亚洲天堂色色| 天天日天天插| 五月天激情网站| 丁香五月婷婷基地| 欧美槡BBBB槡BBB少妇| www五月| 久99| 色香五月天| 新99思思视频| 欧美婷| 天天摸天天高潮天天爽| 国产精品热搜丁香五月婷婷| 亚洲国产精品综合色区| 人人人va亚洲视频在线| 婷婷五月丁香六月综合网| 深爱激情网综合| 可以免费看AV网站| 五月天开心婷婷激情网站| 色爱亚洲| 亚洲国产成人在线| 欧美熟女99| 另类天堂| 无码少妇高潮喷水A片免费| 亚洲妇女熟BBW| 人人肏逼视频在线一区二区| 色爱综合五月| 丁香婷婷网| 开心 五月 综合| 天天模,夜夜模夜夜爽| 婷婷六月色情| 超碰人人操| 99色视频| 三级黄色大片视频| 97人人干。| 久大香蕉| 欧美丁香六月在线观看视频| 五月天色婷婷伊人网| 天天操天天操天天操天天操天天操天天操天天操天天操天天操 | 久久国产色| 免费AV在线| WWW,五月| 成人无码髙潮喷水A片| 成人无码精品1区2区3区免费看| 日韩久久成人| 中日韩狠狠色| 激情婷婷五六月天| 99热免| 婷婷色九月| 九九热在线精品视频| 亚洲视频在线观看| 婷婷丁香色性爱| 六月激情婷婷| www,五月天激情| 天天噜| 99人人干| 天天射色五月天| 六月激情婷婷| 五月成人综合| 综合网五月| 婷婷五月色播天| 六月婷色| Jh7Uf088VHafNm| 999久久久国产精品| 天天色播| 色婷婷色| WWW.桔色成人.COM入口| 天天在线XXX| 色狠狠色| 久久精品夜色噜噜亚洲a∨| 色五月丁香五月五月婷婷| 婷婷五月天激情综合深爱激情 | 97热在线精品| 操碰色一区就去操| 狠狠综合网| 婷婷五月成人| 夜夜久久综合网 | 激情com| 99re8这里只有精品99re8热视频| 婷婷五月天影院| 久久久五月天| 久热AA| 五月天激情婷婷丁香| 综合久久影院| 婷婷激情五月天激情小说| 全亚洲最大的婷婷五月天网站COM| wwwC0maV五月花| 日本五月婷| 一起草日本| 久热这里只有精品性色AV| 五月丁香激情六月| 天天天天操| 久久最新色| 99er6热在线观看精品6| 99成人| 一本色道久久88加勒比—| 天天插天天干天天舔| 五月停停999| 婷婷狠狠综合网入口| 99ri精品视频在线观看| 亚洲无码99| 亚洲综合色成丁香五月色| 精品99视频| 激情五月婷婷中文字幕| 99热成人| 九九综合色| 天天插天天干| 色婷婷丁香女女| 亚洲综合视频天天精品| 伊人久久五月天| 婷婷五月a| 婷婷五月天xxx| 激情另类综合| 蜜桃婷婷狠狠久久| 26uuu成人网| 老师高潮流白浆喷水的A片| 九九热色视频| 可以看的AV| 91精品婷婷国产综合| 人人草人人视| 狠狠色中色| caopeng97日韩| 丁香五月激情五月| 99riAV国产精品视频| 九九久热| 99久久久精品| 五月五婷婷| 99色综合久久| 五月激情婷婷六月丁香| 丁香五月天啪啪| 综合97五月| 中文激情网| 國語久久婷| 91人操| 狠狠色噜噜狠狠| 色色射| 亚洲影院婷婷色| 精品无码99| 1级欧美日韩| 中文字幕色色色| 婷婷五月色综合香五月| 五月丁香狠狠| 视频在线免费观看欧洲乱码| 这里只有精品久久| 婷婷性爱网| 精品五月天| 亚洲国产色婷婷| av国产精品| 激情亚洲色图片丁香综合| 97超碰免费超级在线观看| 开心婷婷五月激情网小说| 六月天婷婷| 99热这里只有精品268| 色综合五月天| 丁香五月大片| 五月婷婷久草| 99热6这里只有精品| 久久丁香九| 九九视屏| AV中文在线| 激情综合久久| 婷婷五月天性| 丁香婷婷激情网站| 丁香五月天电影| 激情五月色综合网| 欧美五月婷婷| 色综合天堂| 激情婷婷| 五月婷婷欧美| 五月婷婷综合激情| 五月天激情.com| 五月天丁香花婷婷| 婷婷综合色| 婷婷亚洲五| 国产熟妇乱子伦hd| 五月天婷婷激情春色小说| 日日操夜夜操中国无码| www.99热在线观看| 五月丁香美女| 亚洲av电影在线| 丁香六月欧美| 91无码视频| 免费AV播放| 九色色| 中文字幕网站在线观看| 五月丁香综合在线| 五月婷婷婷自由综合| 99热www| 五月综合视频| 老司机午夜福利视频金瓶梅| 日本波多野结衣视频| 97操碰在线视频| 六月丁香花婷婷| 怎么样可以看免费的一级av| 99久久婷婷五月综合| 玖玖在线资源视频| 人人操女人| 99热在线观看| www.henhenl| 五月花成人网| 91丨九色丨白浆秘| 婷婷99视频全集高清| ww久久| 艾小青av| 色综合夜夜| 亚洲视频1区| 久热九九| 99九九热视频| 日日爽天天| 丁香五月天在线观看视频| 91n啪啪| 久久婷婷热| 草综合14| 色情一区二区播放| 五月综合亚洲色| 色色五月激情| 日韩成人中文| 丁香五月天视频| 99热色精品| 五月丁香六月婷婷a v| 久久五月网| Www.se.久久| 激情综合五月天| 91干视频| 综合网亚洲| 小视频一区| 五月丁香婷婷爱激情综合网| 激情中文在线| www.1024久久| 日韩AV无码影片| 欧美这里只有精品| 日本美女上人| 色五月丁香婷婷| 色婷婷五月网| 色五月婷婷丁香国产在线| 97人人做| 日本在线99| 热99.com婷婷| 丁香,开心成人,久久| 婷婷丁香五月综合| 99热这里是精品| 国产性爱一级| 色屌丝中文字幕| 男女久久婷婷五月天| 99亚洲综合| 色婷婷电影网| 色色色国产| 色五月婷婷综合在线| 日日操夜夜操中国无码| 爱穴久久| www五月婷婷| 色五月激情五月| 久久激情网| 99热都是精品| 丁香六月激情综合| 能直接看的av网站| 婷婷伊人| 一起草AV| 97色色色| 色噜噜狠狠色综无码久久合欧美| 91久久婷婷| AAA久久久| 久久精品99久久久久久| 日日杆天天| 五月婷激情| 色五月婷婷综合| 激情五月天伊人影院| 色色色.COM| 97婷婷五月| 婷婷丁香色情五月天| 视色综合| 久久精品只有这| 激情六月综合| 色噜噜狠狠色综合日日| 婷婷六月天| 波多野结衣AV无码Porn| 涩综合网| 成人丁香五月天| 婷婷五月天电影网| 五月婷婷色| 久久久国产精品黄毛片| 九九9久九9国产视频| 婷婷97色| 久久全色| 9久热免费视频99| 九九九九毛片| 六月色日韩| 五月丁香婷婷成人伊人网| 《亚洲操B久久免费在线观看,亚洲操B久久在线播放》在线播放 - 高清资源 - 97 | 欧美色婷婷| 久久99热这里只有精品| 五月天婷婷色| 玖玖91| 久操人| 丁香婷婷五月综合影院| 日韩色色色色色| 翔田千里aV中文字幕| 五月天全国最大成人网| 涩五月婷婷| 久久这里99| 久久久久丁香婷婷五月天| 婷婷五月天狠狠色| 色色激情五月天| 五月香婷婷| 任你搞免费视频观看| 国产亚洲色婷婷久久99精品91 www.riverspirits.org www.hnnun.com www.changh | 99在线观看精品| 色色精品色| 色五月开心开心五月激情五月| 婷婷六月激情综合| 久久资源网五月婷| 国外亚洲成AV人片在线观看| 日日操夜夜操中国无码| 99九九热在线观看| 色婷婷综合五月| 婷婷涩涩五月天| 婷婷激情综合| 色色色色色色色色色影院| 五月丁香婷色| 五月婷婷丁香成人网| m色激情网| 国产激情av| 欧美激情性做爰免费视频| 色婷婷色丁香色欲av| 超碰二区| 思思久久思思| 久久婷婷91| 少妇伦子伦精品无吗| 色婷婷色| 777久久精品| 色色色色色色网| 婷婷色综合| 依人大香蕉在钱1| 久久9精品| 99亚洲色| 激情综合网五月天| 五月天堂六月丁香亚州中文字幕久久| 九九人人操| 色婷五月天综合网| 天天视频亚洲| 国产午夜一区二区三区| 婷婷五月天综合久久日| 久久丁香| 久久久久人妻网址| 国自产拍偷拍精品啪啪一区二区| 婷丁香五月天| 五月天激情无码高清| 欧美色色色色色色色| 日韩人妻白浆视频系列| 久色网址| 亚洲激情婷婷| 99久久国产宗和精品1上映| 丁香五月色五月| 天天干天天色天天干| 久久九九网| 伊人成综合五月婷婷| 色色色色色色色综合| 五月婷婷成人| 婷婷99狠| 五月激情网五月综合网| 亚洲第一黄网| 综合婷| 五月婷婷免费视频| 无码操B| 激情综合色婷婷啪啪六月天| 日韩乱玛久久| 色五月婷婷五月天| 玖玖综合网| 99热这里只有精品在线观看| 69超碰在线| 婷婷五月四狠狠| www.99热精品| 婷婷干六月综合旧址| 婷婷五月开心中文字幕色| 成人在线网| 热99在线精品| 精品人妻久久久久| 综合色、色综合| 思思视频这里是精品| 欧美五月婷婷| 亚洲成人av在线播放| 婷婷丁香色五月久久88| 国产午夜成人AV在线播放| 色区久久| 亚洲天堂热| 伊人综合色干| 九九热这里| 97婷婷五月| 99视频这里只有久久精品| 婷婷丁香五月综合| 久久五月天激情美女| 爽极品色| 91狠狠色色丁香婷婷综合久久| 99久久6| www.韩日视频| 亚洲婷婷成人五月天| 99国产精品久久久久久久久久久| 热九九九九| 可以免费看AV网站| 激情五月天。| A A色色| 色狠狠色综合久久久绯色aⅴ影视| 26uuu色噜噜精品一区| 色色com| 久久久人妻不卡| 色欲久久综合| 欧美性爱五月天| 九九99精品| 九热视频| 五月婷婷五月天| 婷婷放心五日爱| 天天爽夜夜操| 超黄亚洲瑟瑟网站| 婷婷五月天网| 2025最新亚洲激情在线| 无码少妇高潮喷水A片免费| 狠狠做五月婷婷| 最近中文字幕大全免费版在线 | 99碰网站| 97久久精品| 婷婷久久网| 深爱激情中文五月天av| 天天日天天操心| 久久这里只有精品07 | 淫五月停停| 丁香五月激情鲁| 日逼影音先锋AV男人资源站| 天天精品视频免费观看| 欧美VA视频| 99在线视频精品| 色综合色色| 午夜丁香婷婷| 人妻在线中文字幕久久| www.第四色99| 五月婷婷丁香五月婷婷丁香| 热99精品视频五月| 99爱视频免费| 婷婷成人丁香色情基地30| 五月丁香亭亭激情操逼网| 人妻久久久久久久久久| 久久天堂婷婷五月| 97AV在线视频| 天天日夜夜B久久| 狠狠婷婷色| 99热网站| 337p大胆噜噜噜噜噜91Av| 99热91| 色噜噜夜夜夜综合网| 色香蕉影院| 婷婷久久五月天亚洲欧美国产日韩在线观看 | 激情五月丁香五月| WWW99热| 激情久久久| 国精产品一区二区三区| 冬月かえでAV无码播放| av九九| 婷婷五月天深爱| 五月天婷婷激情四射综合| 另类激情五月| 凹凸探花电影| 婷婷久久婷婷色五月| 超碰二区| 婷婷另类开心| 99久免费视频| 99爱在线视频| 婷婷五月天六月| 26uuu精品一区二区| 久操婷婷| 怡红院视频| 少妇激情基地| 亚韩精品视频1区| 亚洲综合视频在线| 亚洲婷婷丁香五月亚洲| 亚州婷婷五月激情综合| 五月天激情综合| 婷婷久久亚洲| 久热99| 伦乱人妻| 人人摸人人摸| 日韩99色99| 婷婷五月综合在线| 天天插操| 色色丁香| 亚洲成人黄色网| 另类天堂| 另类图片五月激情| 97人人超| 99精品网| 五月婷婷五月天天| 日韩成人AV在线播放| 超碰在线网站9| 91人人爽狠狠狠| 91精品国产综合久久密臀 | 激情久久久久| 丁香婷在线| 欧美激情丁香五月| 99在线爽| 综合激情网激情五月。| 九九五月天| 超碰啪啪网| 91超碰人人操| 日本久久精品18| 狠狠色狠狠色综合日日91 | 国产精产国品一二三在观看| 超碰a女人的天堂| 激情网开心网| 玖玖视频福利| 欧美日韩国产日本精品四虎网网站物 | 久久黄色网扯| 猫咪伊人久久| a免费在线| 五月丁香啪| 亚洲无码11| 人妻VideOssS人妻高清| 激情五月丁香综合蜜桃| 亚卅毛片| 综久久久| 中文字幕一色哟哟哟哟| 夜夜干 夜夜操| 色色无码| 久色欧美| 天天日人人爽| 5月色婷婷| 91色在线/日韩| 久久码久久无清| se色婷婷视频| 99热| 色色色色综合| 久9久9久9久9久9久9| 九九热视| 五月婷婷自拍视频| 天天操天天操综合| www,8050,午夜三级| 9l视频自拍9l九色9l成人| 五月婷丁香久久综合| 免费黄网不卡AV| 六月婷婷综合| 久久五月丁香| 六月丁香婷| www.久久爱.com| 日本色爽| 五月丁香六月综合激情无码软件亮点| www.五月天。com| 亚洲图色五月天| 中文字幕 中文字幕明步| 九九人人操| 亚洲激情五月| 婷婷婷婷色| 九九九九综合| 成人版视频在线观看| 人人摸人人摸| 色偷偷色婷婷| 婷婷五月天激情文学| 99免费视频在线观看爱| 五月开心激情网| 久久99色色| 免费试看小视频 99| WwW天天干| 99这里只有精品国产| 综合激情啪啪| 蜘蛛女免费观看完整版高清电影 | 久久九九色| 性爱视频99| 国产激情久久久| 国产成人99久久亚洲综合精品| 51XX午夜影福利| 久9视频| 538任你爽| 五月天色色网站| 五月天婷婷色| 国产在这里只有精品| 国产激情综合五月久久| 狠狠操天天干| 天天干天天干天天| 精品夜夜澡人妻无码AV| 香蕉人妻AV久久久久天天| 99久久66综合| 夂夂夂夂夂夂夂夂夂夂夂夂夂夂夂夂夂夂夂亚洲亚洲亚洲亚洲亚洲亚洲亚洲亚洲色 | 久99综合婷婷| 婷婷五月丁香综合| www.99视频| 夜夜操狠狠操| 亚洲深喉AV| 影音先锋一区二区资源站| 久久99免费视频网站| 婷婷色基地在线看| 成人免费在线电影| 91热99| 秋霞午夜理论| 婷婷五月天激情视频| 色婷婷综合网站| 性爱视频99| 日韩99视频| 九月婷婷综合| 中字幕视频在线永久在线观看免费| 亚洲无AV在线中文字幕| 五婷婷综合网| 五月叮香啪| 久久久香| 久这里只有精品| 五月天婷婷深深爱| 26uuu精品一区二区| 性视频久久| 99九九精品| 欧美 色婷婷| 色月丁| 99热在线观看| 欧美黑人巨大猛烈cuckold| 亚洲人人操BD| 99人妻碰碰碰久久久久视| 99在线观看| 婷婷成人基地| 五他月天啪啪啪| 人妻AV在线观看| www.精品99| 婷婷开心久久| 久婷| 国产成人精品一区二三区熟女在线| 婷婷综合在线网| 91九色熟女| 激情5月婷婷狠狠干| 婷婷六月五月| 国产超碰在线| 婷婷五月丁香基| 99色日本| 99热热九九| 日韩视频99| 五月激情小说网| 九九九九九九热| 日韩久久色| 丁香五月天欧美| 伊人玖玖精品| 图片区 小说区 区 亚洲五月| 99在线视频喷水| site:901-07.com| www,99热| 看片视频在线免费日产在线看| 99久久综合狠狠综合久久| 91视频精品99| 狠狠狠五月婷婷六月丁香| www.yw色| 4399无码视频| 超碰9| 久久精品66| 狠狠操狠狠爱| 91久久久久| 五月天狠狠网站| 色女伊人| 色色色五月婷婷| 欧美久人人| 婷婷五月天777| 久久精彩视频| 爽tv | 日本久热| 丁香婷婷婷五月| 激情六月婷婷| 久操97| xfplayav在线| 欧美操人| 婷婷色情五月| 白天AV月月| 综合色播| 婷婷五月激情综合啪啪| 天干天天干天天天天天| 色色色婷婷五月| 丁香花综合永久入口| 中文网AV| av在线免费网站| 亚洲视频在线网站| 五月丁香狠狠爱| 九九婷婷网五月天| 丰满少妇猛烈A片免费看观看| 9|无码久久久久久| 婷婷五月丁香手机在线视频| 五月丁香六月激情综合| aaa久久| 婷婷丁香色五月| 无码人妻丰满熟妇奶水区码| 婷婷四色五月| jiZZdr| 丁香五月天大香蕉啪啪| 深爱五月激情综合| 操操国产| 色久99| 五月丁香激情深爱婷婷| 超碰在线91| 婷婷五月天久久久| 亚洲VA口| 婷婷丁香五月社区亚洲| 丁香五月婷婷丫| 超碰在线91| 91视频五月丁香| 亚洲日日操| 91九色超碰| 婷婷五月深深的爱| 丁香六月五月天| 大香蕉久久久| A久久| 久久久久五月丁香| 欧美婷婷五月| 国产熟妇乱子伦hd| 99久热这里有精品| 在线不卡视频| 久9热视频在线观看| 亚洲综合激情五月久久| 狠狠爱五月婷婷综合六月| 婷婷五月丁香婷婷| 嫩草AV久久伊人妇女超级A| 激情五月天婷婷直播| AV在线观看网站| 91精品无码久久久久久五月天| 国产精品色婷婷AV综合色色| 伊人婷婷99热精品| 东北婷婷五月天| 欧美人与性动交CCOO| 五月网激情| 五月开心网| 欧美色五月| 99热在线精品观看| 大香蕉婷婷丁香天堂AV| 大香蕉婷婷丁香视频在线| 久9热视频| 综合色色婷婷| av线电影| 一起草无码| 色99自拍| 六月婷婷激情图片| 五月丁香成人| 色五月色五天色情网| 国产精品99久久久久久猫咪| 啪啪婷婷五月天激情| 日本99在线视频| 久久久激情视频| 综合婷婷久久| 99久久网站| 五月婷婷在线短视频| 激情开心五月天| 色色色在线免费视频| 热久久这里只有精品| 五月婷丁香在线视频在线| 欧美日本免费一道免费视频| 丁香五月天激情小说| 精品一区久热| 天天爽天天日天天舔| 五月婷婷国产| 久久九九@| 色婷婷97| 久久综合激情| 丁香五月日本| 99青青草99| 这里只有精品免费视频| 伊人婷婷91| 91精品久久久久| 婷婷六月丁香在线| 国产黄大片在线观看画质优化| 欧美综合五月丁香六月婷| 日噜噜色| 99在线免费视频| 男女99免费视频| 激情久久久| 六月丁香五月激情婷婷| 97人人干。| 丁香六月狠狠干| 色热久资源| 亚洲精品无AMM毛片| 噜噜噜噜噜色| 国产一区18| 色婷婷丁香五月| 伊人婷婷激情| 91久久九九| 亚洲综合色色| 熟女重口味αV| 久热99狠| 久久久99免费视频| 色狠狠激情五月| 中文字幕在线视频播放| 五月婷婷激情网| 色情性爱视频网址| 成人.在线日韩| 五月天啪啪啪| 婷婷久草| 五月天sesese| 激情人妻综合| 综合婷婷六月| 国产91在线视频| 99ri在线| 九九热视频免费观看| 99精品女人天堂| 99久久综合网| 婷婷五月美女直播| 婷婷精品在线| 国产91资源在线| 在线观看婷婷5月| 精品一区二区三区四区五区六区介绍| 国产特黄色精品一区二区三区精品无广告 | AV 3P| 亚洲xx网| 久久久久久久人妻| 久久婷婷五月免费视频| 国产超碰在线| 超碰2021| 这里只有精品免费视频| 亚洲狠狠狠| 超碰91在线| 校园春色亚洲色| 99色婷婷视频| 天天综合网亚洲综合网| 99色综合网| 伊人99久久| 日韩九区| 五月天基地| 色情综合| 亚洲精品九九| 97色色色| 日本五月天激情| www.久久综合| 婷婷色中文字幕| 99久久极情精品一区| 妇激情基地| 久久久久九九九九视屏小说88| 九九99在线免费在线观看视频| 激情婷婷丁香色五月| www婷婷| 五月婷婷碰碰| 这里只有精品视频免费在线观看| 99热这里只有精品2| 五月天婷婷一起草| 九九热婷婷| 国产五月视频| 99性视频| 天天日天天爽夜夜爽| 久久久久综合激动五月天| 激情综合色图| 影音先锋男士资源网一区| 久久这里只有精品99| 99热这里只有精品免费| 亚洲看av的网站| 啪啪综合网| 日韩精品99久久| 91av传媒高清在线视频网| 婷婷丁香在线| 五月丁香六月婷婷网| 五月丁香网中文字幕| 大香蕉五月天婷婷| 9热久久| 大香伊人久色| 超碰碰碰碰| 亚洲精品亚洲人成人网| 无人精品在线视频| 成 久久| 九九视频这里只有精品在线播放| 亚洲 视频 导航 一区| 丁香五月天日韩无码| 亚洲亚洲人成综合网络| 色色色色色色网| xx久久| 久久久这里有精品| 亚洲bt丁香五月天婷婷激情小说| 伊人天天色| 五月丁香六月婷婷,婷|