[英]C++ “Could not deduce template argument” when using std::async
一般来说,我对C ++和编程还是很陌生。 实际上,我制定了一种类似于mergesort的排序算法。 然后,我尝试使其成为多线程。
std::future<T*> first = std::async(std::launch::async, &mergesort, temp1, temp1size);
std::future<T*> second = std::async(std::launch::async, &mergesort, temp2, temp2size);
temp1 = first.get();
temp2 = second.get();
但是似乎我的编译器无法确定要使用哪个模板,因为两次出现相同的错误。
Error 1 error C2783: 'std::future<result_of<enable_if<std::_Is_launch_type<_Fty>::value,_Fty>::type(_ArgTypes...)>::type> std::async(_Policy_type,_Fty &&,_ArgTypes &&...)' : could not deduce template argument for '_Fty'
Error 2 error C2784: 'std::future<result_of<enable_if<!std::_Is_launch_type<decay<_Ty>::type>::value,_Fty>::type(_ArgTypes...)>::type> std::async(_Fty &&,_ArgTypes &&...)' : could not deduce template argument for '_Fty &&' from 'std::launch'
这些错误使我相信std :: async重载了两个不同的模板,一个用于指定的策略,一个用于未指定的模板,并且编译器无法选择正确的模板(我使用的是Visual Studio Express 2013)。 那么,如何为编译器指定适当的模板? (做std::future<T*> second = std::async<std::launch::async>(&mergesort, temp2, temp2size);
似乎不起作用,我得到了无效的模板参数,键入预期的)。 有没有更好的方法可以完全做到这一点? 谢谢!
您需要为mergesort
指定模板参数。 异步不够聪明,无法自行解决。 下面是一个基于迭代器的示例。 它还将当前活动线程用作递归点,而不是燃烧等待其他两个线程的线程句柄。
我警告您,有更好的方法可以做到这一点,但对此进行调整可能就可以满足您的需求。
#include <iostream>
#include <algorithm>
#include <vector>
#include <thread>
#include <future>
#include <random>
#include <atomic>
static std::atomic_uint_fast64_t n_threads = ATOMIC_VAR_INIT(0);
template<typename Iter>
void mergesort(Iter begin, Iter end)
{
auto len = std::distance(begin,end);
if (len <= 16*1024) // 16K segments defer to std::sort
{
std::sort(begin,end);
return;
}
Iter mid = std::next(begin,len/2);
// start lower parttion async
auto ft = std::async(std::launch::async, mergesort<Iter>, begin, mid);
++n_threads;
// use this thread for the high-parition.
mergesort(mid, end);
// wait on results, then merge in-place
ft.wait();
std::inplace_merge(begin, mid, end);
}
int main()
{
std::random_device rd;
std::mt19937 rng(rd());
std::uniform_int_distribution<> dist(1,100);
std::vector<int> data;
data.reserve(1024*1024*16);
std::generate_n(std::back_inserter(data), data.capacity(),
[&](){ return dist(rng); });
mergesort(data.begin(), data.end());
std::cout << "threads: " << n_threads << '\n';
}
产量
threads: 1023
您必须相信我,最终向量已排序。 不会将16MB的值转储到此答案中。
注意:此文件在Mac上使用clang 3.3进行了编译和测试,并且没有问题。 不幸的是,我的gcc 4.7.2死了,因为它会在共享计数中止时抛出cookie,但是我对它所在的libstdc ++或VM并不抱有很高的信心。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.