[英]Using std::thread to call std::sort directly
How can I make a thread execute std::sort()
directly, without creating an intermediate function?如何让线程直接执行
std::sort()
,而不创建中间 function?
Something like:就像是:
std::thread t1(std::sort, data.begin(), data.end());
My (playground:) idea is letting each thread sort half of the vector and then merge it:我的 (playground:) 想法是让每个线程对向量的一半进行排序,然后将其合并:
#include <vector>
#include <thread>
#include <iostream>
#include <algorithm>
// Type your code here, or load an example.
void myfunc(std::vector<int>& data) {
std::sort(data.begin(), data.begin() + data.size() / 2);
return;
}
int main()
{
std::vector<int> data = { 1, 8, 123, 10, -3, 15, 2, 7 };
std::thread t1(myfunc, std::ref(data)); // works
//std::thread t1(std::sort, data.begin(), data.begin() + data.size() / 2); // doesn't
std::sort(data.begin() + data.size() / 2, data.end());
t1.join();
std::inplace_merge(data.begin(), data.begin() + data.size() / 2, data.end());
for (auto x : data)
std::cout << x << "\n";
}
Compiler error, when using the commented line instead of the one above (I used an online code editor):编译器错误,当使用注释行而不是上面的行时(我使用在线代码编辑器):
error: no matching function for call to 'std::thread::thread(<unresolved overloaded function type>, std::vector<int>::iterator, __gnu_cxx::__normal_iterator<int*, std::vector<int> >)'
16 | d t1(std::sort, data.begin(), data.begin() + data.size() / 2); // doesn't
| ^
In file included from /usr/include/c++/11/thread:43,
from /tmp/bBJEjs0nrj.cpp:2:
/usr/include/c++/11/bits/std_thread.h:127:7: note: candidate: 'template<class _Callable, class ... _Args, class> std::thread::thread(_Callable&&, _Args&& ...)'
127 | thread(_Callable&& __f, _Args&&... __args)
| ^~~~~~
/usr/include/c++/11/bits/std_thread.h:127:7: note: template argument deduction/substitution failed:
/tmp/bBJEjs0nrj.cpp:16:75: note: couldn't deduce template parameter '_Callable'
16 | d t1(std::sort, data.begin(), data.begin() + data.size() / 2); // doesn't
| ^
In file included from /usr/include/c++/11/thread:43,
from /tmp/bBJEjs0nrj.cpp:2:
/usr/include/c++/11/bits/std_thread.h:157:5: note: candidate: 'std::thread::thread(std::thread&&)'
157 | thread(thread&& __t) noexcept
| ^~~~~~
/usr/include/c++/11/bits/std_thread.h:157:5: note: candidate expects 1 argument, 3 provided
/usr/include/c++/11/bits/std_thread.h:121:5: note: candidate: 'std::thread::thread()'
121 | thread() noexcept = default;
| ^~~~~~
/usr/include/c++/11/bits/std_thread.h:121:5: note: candidate expects 0 arguments, 3 provided
Desired output:所需的 output:
-3,1,27,8,10,15,123
The most direct translation of the original code uses a template instantiation:原始代码的最直接翻译使用模板实例化:
std::thread t1(std::sort<std::vector<int>::iterator>,
data.begin(), data.end());
std::sort()
is a function template, and as such cannot be passed as-is to a function that expects a concrete functor (a type that behaves like a function). std::sort()
是一个 function 模板,因此不能按原样传递给需要具体仿函数(一种行为类似于函数的类型)的 function。 You need to either cast std::sort
to the correct function pointer type, or else wrap it in some way that lets the compiler figure out which version of std::sort()
you are trying to call.您需要将
std::sort
转换为正确的 function 指针类型,或者以某种方式包装它,让编译器确定您尝试调用哪个版本的std::sort()
。
The easiest way to deal with that is to use a lambda expression to wrap the call to std::sort()
so that the compiler can do the template deduction for you.处理这个问题的最简单方法是使用 lambda 表达式来包装对
std::sort()
的调用,以便编译器可以为您执行模板推导。 That can look like this:这看起来像这样:
std::thread t1([&](){ std::sort(data.begin() + data.size() / 2, data.end()); });
You can use a lambda:您可以使用 lambda:
std::thread t1([&data](){std::sort(data.begin() + data.size() / 2, data.end());});
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.