【发布时间】:2018-11-22 22:23:48
【问题描述】:
我正在尝试使用 STL 的样式创建一个函数来生成可变数量的输入范围的笛卡尔积。我的基本格式是该函数接受一个固定范围和一个输出范围的开始,然后是一个可变数量的双向输入迭代器。
template <
typename BidirectionalIterator,
typename OutputIterator,
typename... Args
>
void cartesian_product(
BidirectionalIterator first,
BidirectionalIterator last,
OutputIterator result,
Args&&... args
);
我对@987654322@ 的想法是我用它制作一个tuple,然后我遍历那个tuple 以提取元素。这需要我遵循几个基本步骤:
- 从
args创建一个tuple - 取消引用新创建的
tuple中的每个迭代器 - 依次递增
tuple中的每个迭代器,以便我们获得范围内值的所有可能组合。
详细说明第 3 步:如果我们有两个集合 A = {0, 1} 和 B = {2, 3},笛卡尔积 A x B = {(0, 2), (0, 3), (1, 2), (1, 3)}.
我可以像这样做第一步:
auto arg_tuple = std::make_tuple(std::forward<Args>(args)...);
第二步,我不太确定。我想我会以某种方式将 push_back 元素设置为临时元组,然后将 *result 设置为等于该临时元组。 ostream 实现这一点的方式让我有点灵感,所以我认为这可以派上用场:
template <typename Tuple, typename T>
auto operator<<(const Tuple &lhs, const T &rhs)
-> decltype(std::tuple_cat(lhs, std::make_tuple(rhs)))
{
return std::tuple_cat(lhs, std::make_tuple(rhs));
}
第三步可能很简单。我可以结合这样的东西:
template <typename T>
auto pre_increment(T &x) -> decltype(++x) {
return ++x;
}
这里有 for_each 的 3,000 个实现之一,用于 tuple。
奇怪的是我没有正确地利用 C++14 来实现这一点。到目前为止,我的教育完全是 C++11 中难度较低的部分。
如果你想推荐我使用boost::fusion,谢谢,但我不想使用它。
【问题讨论】: