C++11 use-case for piecewise construct of pair and tuple?

W N3059 znalazłem opis fragmentarycznej budowy par (i krotek) (i jest to w nowym standardzie).

Ale nie widzę, kiedy powinienem go użyć. Znalazłem dyskusje na temat emplace i nie-kopiowalnych Bytów, ale kiedy wypróbowałem to, nie mogłem stworzyć przypadku, w którym potrzebuję piecewiese_construct lub może zobaczyć korzyści wydajności.

Przykład. Myślałem, że potrzebuję klasy, która jest nie do skopiowania, Ale movebale "required": {]}

struct NoCopy {
  NoCopy(int, int) {};
  NoCopy(const NoCopy&) = delete; // no copy
  NoCopy& operator=(const NoCopy&) = delete; // no assign
  NoCopy(NoCopy&&) {}; // please move
  NoCopy& operator=(NoCopy&&) {}; // please move-assign
};

Spodziewałem się wtedy, że standardowa konstrukcja pary zawiedzie:

pair<NoCopy,NoCopy> x{ NoCopy{1,2}, NoCopy{2,3} }; // fine!
Ale tak się nie stało. Właściwie, to jest to, czego i tak się spodziewałem, bo "przenoszenie rzeczy", a nie kopiowanie go wszędzie w stdlib, jest to powinno być.

Dlatego nie widzę powodu, dla którego miałbym to zrobić, albo tak:

pair<NoCopy,NoCopy> y(
    piecewise_construct,
    forward_as_tuple(1,2),
    forward_as_tuple(2,3)
); // also fine
  • więc, co to jest usecase ?
  • jak i kiedy używać piecewise_construct?
Author: chema989, 2011-05-28

1 answers

Nie wszystkie typy mogą być przenoszone bardziej efektywnie niż kopiowane, a dla niektórych typów może mieć sens nawet jawne wyłączenie zarówno kopiowania, jak i przenoszenia. Rozważmy std::array<int, BIGNUM> jako przykład dawnego rodzaju typu A.

Z FUNKCJAMI emplace i piecewise_construct wynika, że taka klasa może być skonstruowana w miejscu, bez potrzeby tworzenia tymczasowych instancji do przeniesienia lub skopiowania.

struct big {
    int data[100];
    big(int first, int second) : data{first, second} {
        // the rest of the array is presumably filled somehow as well
    }
};

std::pair<big, big> pair(piecewise_construct, {1,2}, {3,4});

Porównaj powyższe z pair(big(1,2), big(3,4)) gdzie dwa tymczasowe big obiekty być tworzone, a następnie kopiowane - a przenoszenie tu wcale nie pomaga! Podobnie:

std::vector<big> vec;
vec.emplace_back(1,2);

Głównym przypadkiem użycia do fragmentarycznego konstruowania pary jest umieszczenie elementów w map lub unordered_map:

std::map<int, big> map;
map.emplace(std::piecewise_construct, /*key*/1, /*value*/{2,3});
 29
Author: JohannesD,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-05-28 17:55:53