C++20嚐鮮:結構化繫結

放鬆結構化繫結定製點查詢規則

P0961R1

結構化繫結的 lambda 捕獲與儲存類說明符

P1091R3

P1381R1

允許到可訪問成員的結構化繫結

P0969R0

結構化繫結的Lambda捕獲和儲存類說明符

結構化繫結允許有[[maybe_unused]]屬性、static和thread_local說明符。而且,現在可以在lambda中按值或按引用捕獲它們。注意,繫結的位欄位只能透過值捕獲。

#include struct S{ int a: 1; int b: 1; int c;};static auto [A,B,C] = S{};void f(){ [[maybe_unused]] thread_local auto [a,b,c] = S{0,0,1}; [[maybe_unused]]auto l = [=](){ return a + b + c; }; std::cout << l() << std::endl; [[maybe_unused]]auto m = [&](){ // error, can‘t capture bit-fields ’a‘ and ’b‘ by-reference // return a + b + c; return c; };} int main(){ f(); std::cout << A << std::endl; return 0;}

C++20嚐鮮:結構化繫結

線上測試

https://wandbox。org/nojs/gcc-headhttps://wandbox。org/nojs/clang-head

放鬆結構化繫結自定義點查詢規則

將型別分解為結構化繫結的一種方法是透過類似元組的 API。它由三個“函式”組成:std::tuple_element、std::tuple_size 和兩個 get 選項:e。get() 或 get(e),其中第一個優先於第二個。也就是說,成員 get() 優先於非成員。想象一個型別有 get() 但它不適用於類似元組的 API,例如 std::shared_ptr::get()。這種型別無法分解,因為編譯器會嘗試使用成員 get() 並且它不起作用。現在,此規則已修復為僅當成員版本是模板且其第一個模板引數是非型別模板引數時才首選成員版本。

#include #include struct X : private std::shared_ptr{ std::string payload {“hello”};};// due to new rules, this function is used instead of std::shared_ptr::gettemplatestd::string& get(X& x) { if constexpr(N==0) return x。payload;}namespace std { template<> class tuple_size : public std::integral_constant {}; template<> class tuple_element<0, X> { public: using type = std::string; };}void f(){ X x; auto& [payload] = x; std::cout << payload << std::endl; } int main(){ f(); return 0;}

允許結構化繫結到可訪問的成員

此修復不僅允許對公共成員進行結構化繫結,還允許對結構化繫結宣告上下文中可訪問的成員進行結構化繫結。

#include struct A { friend void f();private: int i;};void f() { A a; auto x = a。i; // OK auto [y] = a; // Ill-formed until C++20, now OK} int main(){ f(); return 0;}