在c++中使用线程按顺序填充向量
Filling a vector in order using threads in C++
我正在尝试用数据填充一个巨大的双向量(1929x1341,甚至可能更大),现在需要大约10秒才能完成。
作为参考,这是目前为止的代码:
vector<vector<float>> vector1;
for (int x = 0; x < mapWidth; x++) {
vector<float> vector2;
for (int y = 0; y < mapHeight; y++) {
int someNumber = calculateNumber(x,y);
vector2.push_back(someNumber);
}
vector1.push_back(vector2);
}
我想我应该能够通过把工作分成不同的线程来减少工作时间。具体来说,我可以把第二个for循环分成它们各自的线程。
不幸的是,我不擅长线程。主要的问题是向量需要按顺序填充。所以我不能把第二个向量单独的放到它们自己的线程里,然后再把它们组合起来,因为那样会让它们变成半随机的顺序。我已经研究了互斥锁和条件变量,但我无法找到一个很好的解决方案来解决这个特定的问题。
有谁愿意帮我一下吗?你可以这样做:
std::vector<std::vector<float>> vector1(mapWidth);
std::vector<std::thread> threads;
for (int x = 0; x < mapWidth; x++) {
threads.emplace_back([&, x]() {
for (int y = 0; y < mapHeight; y++) {
int someNumber = calculateNumber(x, y);
vector1[x].push_back(someNumber);
}
});
}
for (int x = 0; x < mapWidth; x++) {
threads[x].join();
}
这里棘手的部分是让几个线程同时工作。当其中一个线程空闲时,另一个线程接管创建新的vector。
在这种情况下,std::future很有用,因为它允许我们同步线程间共享的结果集合。可以为每个线程启动一个异步任务,并在std::future对象中收集其结果。我使用std::async创建线程:
#include <queue>
#include <vector>
#include <future>
#include <iostream>
int width = 5;
int height = 3;
float calculateNumber(int x, int y)
{
return x * y;
}
std::vector<float> fill_info(int x, int height)
{
std::vector<float> v;
v.reserve(height);
for(int y = 0; y < height; ++y)
v.push_back(calculateNumber(x, y));
return v;
}
int main()
{
// our thread limit
const auto number_of_threads = std::thread::hardware_concurrency();
// our data container
std::vector<std::vector<float>> v;
// queue of asynchronous (shared) results
std::queue<std::future<std::vector<float>>> q;
for(int x = 0; x < width; x++)
{
if(q.size() >= number_of_threads)
{
v.push_back(q.front().get()); // blocks until thread is done
q.pop();
}
q.emplace(std::async(std::launch::async, fill_info, x, height));
}
// collect uncollected results
while(!q.empty())
{
v.push_back(q.front().get()); // blocks until thread is done
q.pop();
}
std::cout << v.size()<< 'n';
for(int x = 0; x < width; ++x)
for(int y = 0; y < height; ++y)
std::cout << "{" << x << ", " << y << "}: " << v[x][y] << 'n';
}
输出:{0, 0}: 0
{0, 1}: 0
{0, 2}: 0
{1, 0}: 0
{1, 1}: 1
{1, 2}: 2
{2, 0}: 0
{2, 1}: 2
{2, 2}: 4
{3, 0}: 0
{3, 1}: 3
{3, 2}: 6
{4, 0}: 0
{4, 1}: 4
{4, 2}: 8
相关文章:
- CMake-按正确顺序将项目与C运行时对象文件链接
- 函数调用中参数的顺序重要吗
- 在c++中用vector填充一个简单的动态数组
- 为什么不;名字在地图上是按顺序排列的吗
- 将Integer转换为4字节的unsined字符矢量(按大端字节顺序)
- 如何使用用户输入在C++中正确填充2D数组
- 数到第n个楼梯的路(顺序无关紧要)
- 如何找到大小'x'数组是否完全填充,在C++?
- 优先顺序:智能指针和类析构函数
- 在循环中按顺序遍历成员变量
- 独立读取-修改-写入顺序
- Cuda C++:设备上的Malloc类,并用来自主机的数据填充它
- 以特殊顺序C++填充矩阵
- 在插入顺序已知时填充 Eigen3 稀疏矩阵的策略
- 是否存在以相反顺序填充缓冲区的MEMSET函数
- 结构对齐填充、最大填充大小和结构成员顺序
- 从顺序文件填充二维数组
- 如何加快非顺序数组填充
- 如何在保持其顺序的同时填充整数数组
- 在c++中使用线程按顺序填充向量