Как именно выполняется std :: async? - PullRequest
0 голосов
/ 27 мая 2018

Интересно, как работает следующий код?

#include <thread>
#include <future>
#include <set>
#include <iostream>
struct Task;
std::set<const Task*> dead_tasks;
struct Task
{
   ~Task() { dead_tasks.insert(this); std::cout << "dtor\n";}
   Task() { std::cout << "ctor\n";}
   Task(Task&&) { std::cout << "move-ctor\n";}
   void operator()() const { std::cout << "func()\n"; }
};
int main(){
   std::cout << dead_tasks.size() << '\n';
   std::async(std::launch::async, Task());
   std::cout << dead_tasks.size() << '\n';
}

Этот код печатает

0 ctor move-ctor move-ctor dtor func () dtor dtor 3

Если мы используем std :: launch :: deferred вместо std :: launch :: async, мы получим

0 ctor move-ctor move-ctor dtor dtor dtor 3 dtor 3

Так что в последнем случае мы пропускаем вызов функции-члена.Зачем?Я могу понять наличие вызова конструктора по умолчанию и вызова конструктора перемещения.Task () вызывает конструктор по умолчанию, затем std :: async выполняет вызов конструктора перемещения ... Однако я пропустил идею второго вызова конструктора перемещения и вызова функции-члена.Я могу думать, что конструктор второго хода вызывается std :: future, не так ли?

1 Ответ

0 голосов
/ 27 мая 2018

Так что в последнем случае мы пропускаем вызов функции-члена.Почему?

Потому что вызов, ну, в общем, отложен.Он начнется только после того, как вы фактически запросите его результаты, например, позвонив get() на будущее (чего вы не сделали):

auto fut = std::async(std::launch::deferred, Task());
fut.get();

Я могу подумать, что конструктор второго ходавызывается std :: future, не так ли?

Это скорее зависит от реализации, будет ли и сколько вызовов будет у конструктора копирования.Создание его, например, в clang, дало мне даже три вызова конструктору перемещения.Таким образом, просто не беспокойтесь об этом.Но если вы это сделаете, вы должны посмотреть сами реализации стандартной библиотеки, если таковые имеются.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...