我想要一个具有此定义的函数:
vector<vector<int>> create_lists(int no_lists, int no_per_list)
第一个参数是子列表的编号,第二个参数是每个子列表的项目数。每个列表应包含一系列整数的子范围,因此调用
create_lists(10,10);
将创建10个子列表,第一个从0到9,第二个从10到19,依此类推。
我已经完成了它的几个版本,但它们都感觉很笨拙。有没有一个漂亮而优雅的方法呢?
答案 0 :(得分:8)
我很少有机会说“使用std::iota
”,所以我不会错过这个!
std::vector<std::vector<int>> create_lists(int no_lists, int no_per_list)
{
std::vector<std::vector<int>> v(no_lists,
std::vector<int>(no_per_list));
for (int i = 0; i < no_lists; ++i) {
std::iota(v[i].begin(), v[i].end(), no_per_list * i);
}
return v;
}
答案 1 :(得分:1)
我会创建2d向量,其默认值为
std::vector<std::vector<int>> temp(no_lists, std::vector<int>(no_per_list));
然后我将遍历每个向量并使用
将它们transform
转换为序列值
for (auto & e : temp)
std::transform(e.begin(), e.end(), e.begin(), [](int foo){static int counter = 0; return counter++;});
将所有功能放在一起的是:
std::vector<std::vector<int>> create_lists(int no_lists, int no_per_list)
{
int counter = 0;
std::vector<std::vector<int>> temp(no_lists, std::vector<int>(no_per_list));
for (auto & e : temp)
std::generate(e.begin(), e.end(), [&counter](){return counter++;});
return temp;
}
你可以看到它在 Live Example
中运行答案 2 :(得分:0)
这可能是最不令人兴奋的答案,但我可能只是使用两个for循环。这种方式对我来说似乎最不模糊和最快,这意味着代码以后更容易理解
std::vector<std::vector<int>> create_lists(int no_lists, int no_per_list)
{
std::vector<std::vector<int>> lol(no_lists, std::vector<int>(no_per_list));
int count = 0;
for(auto &list : lol)
for(auto &v : list)
{
v = count;
++count;
}
return lol;
}
这比一个严格必要的分配和释放更多(传递给vector<int>
构造函数的临时vector<vector<int>>
),但是试图避免这种情况会使代码稍微复杂一些并且可能不会产生太大的影响差异(无论如何你做no_lists+1
分配)。