从转换后的范围构建新容器

Construct new container from transformed range

本文关键字:构建 新容器 范围 转换      更新时间:2023-10-16

在我的代码中,我经常需要从以前转换的范围中创建一个新容器。到目前为止,我已经使用了boost::adaptors::transformedboost::copy_range的组合来完成这项工作,认为容器的构造函数应该能够预先分配必要的内存。不幸的是,我注意到boost::adaptors::transform返回一个SinglePassRange,我不确定该范围的大小是否可以在恒定时间内确定。

namespace boost {
template <typename SeqT, typename Range>
inline SeqT copy_range(const Range& r)
{
return SeqT(boost::begin(r), boost::end(r));
}
}
auto ints = std::vector<int>{...};
auto strings = boost::copy_range<std::vector<std::string>>(
boost::adaptors::transform(ints, [](auto val) { 
return std::to_string(val); 
}));

所以我的问题是:从一个转换的范围构建一个新容器的最佳通用方法是什么?

您可以使用boost::adapter::transformed。文档规定输入范围必须至少为SinlgePassRange,但也说明:

  • 返回范围类别:rng的范围类别

SO如果输入范围是随机访问,则输出范围也是。这消除了你的担忧。

std::transform是C++11及以上版本中的方法:

std::set<int> ints = {1,2,3,1};
std::vector<std::string> strings;
std::transform(ints.begin(), ints.end(), std::back_inserter(strings), [] (int i) {
return std::to_string(i)});

使用此选项,您只能将变换应用于给定范围内的每个元素。如果您还想进行一些过滤,可以使用std::copy_If。我建议你仔细研究一下标题,它充满了宝石。

编辑:添加了back_inserter