我在C ++中第一次使用线程,我想知道我的代码有什么问题。
我正在研究Boruvka的算法,我想为找到组件最短的Edge做出线程。
这是我的代码:
std::vector<std::thread> threads;
std::vector<Edge> minEdges;
for (auto g: components) {
Edge minEd;
minEdges.push_back(minEd);
threads.push_back(std::thread (findPath, g, std::ref(minEdges.back())));
}
for (auto &i : threads) {
i.join();
}
for (Edge edge:minEdges) {
if (!contains(mst, edge)) {
addEdge(&mst, edge.n1, edge.n2, edge.weight);
}
}
void findPath(Graph &component, Edge &edge)
//finds cheapest edge
对于exlanation,我想给组件和minEdges
中元素的引用,其中将存储最便宜的边缘。然后我想加入所有线程并将所有最小边缘放到mst。
这段代码在线给我一个错误,我把线程推送到向量,但我找不到原因。你能告诉我吗?
错误消息(我刚刚删除了文件的路径):
In instantiation of 'struct std::_Bind_simple<void (*(Graph, std::reference_wrapper<Edge>))(Graph&, Edge&)>':
/usr/lib/gcc/x86_64-pc-cygwin/5.4.0/include/c++/thread:142:59:
required from 'std::thread::thread(_Callable&&, _Args&& ...) [with _Callable = void (&)(Graph&, Edge&); _Args = {Graph&, std::reference_wrapper<Edge>}]'
graph.cpp:232:82: required from here
/usr/lib/gcc/x86_64-pc-cygwin/5.4.0/include/c++/functional:1505:61: error: no type named 'type' in 'class std::result_of<void (*(Graph, std::reference_wrapper<Edge>))(Graph&, Edge&)>'
typedef typename result_of<_Callable(_Args...)>::type result_type;
/usr/lib/gcc/x86_64-pc-cygwin/5.4.0/include/c++/functional:1526:9: error: no type named 'type' in 'class std::result_of<void (*(Graph, std::reference_wrapper<Edge>))(Graph&, Edge&)>'
_M_invoke(_Index_tuple<_Indices...>)
^
^
感谢您的回答。
答案 0 :(得分:0)
几点......
不要修改已被其他线程使用的向量(添加到向量可以移动其他元素)
迭代引用,而非临时(auto g
)
尽可能选择emplace_back
可选择尝试lambda语法
使用同步来确保按照您认为的顺序发生事情(在您的情况下不需要 - 线程创建充当内存栅栏)
std::vector<Edge> minEdges;
for (auto &g: components) {
minEdges.emplace_back();
}
std::vector<std::thread> threads;
for (size_t i=0; i<components.size(); ++i) {
threads.emplace_back([&]{findPath(components[i], minEdges[i]);});
}
// rest of code...