Во-первых, если вы объявляете std::packaged_task
для получения аргументов, вы должны передать их operator()
, а не конструктору.Таким образом, в одном потоке вы можете сделать:
std::packaged_task<int(int,int)> task(&ackermann);
auto f=task.get_future();
task(3,11);
std::cout<<f.get()<<std::endl;
Чтобы сделать то же самое с потоком, вы должны переместить задачу в поток и также передать аргументы:
std::packaged_task<int(int,int)> task(&ackermann);
auto f=task.get_future();
std::thread t(std::move(task),3,11);
t.join();
std::cout<<f.get()<<std::endl;
Кроме того, вы можете связать аргументы непосредственно перед созданием задачи, и в этом случае сама задача теперь имеет подпись, которая не принимает аргументов:
std::packaged_task<int()> task(std::bind(&ackermann,3,11));
auto f=task.get_future();
task();
std::cout<<f.get()<<std::endl;
Опять же, вы можете сделать этои передать его в поток:
std::packaged_task<int()> task(std::bind(&ackermann,3,11));
auto f=task.get_future();
std::thread t(std::move(task));
t.join();
std::cout<<f.get()<<std::endl;
Все эти примеры должны работать (и работают как с g ++ 4.6, так и с MSVC2010 и моей just :: thread реализацией библиотеки потоков),Если что-то не так, то есть ошибка в используемом вами компиляторе или библиотеке.Например, библиотека, поставляемая с g ++ 4.6, не может обрабатывать передаваемые объекты только для перемещения, такие как std::packaged_task
до std::thread
(и, следовательно, не обрабатывает 2-й и 4-й примеры), так как она использует std::bind
в качестве детали реализации,и что реализация std::bind
неправильно требует, чтобы аргументы были копируемыми.