c++中的循环和python中的一样(基于范围的for)
Cycles in c++ like in python (range-based for)
在c++中像在python中那样做循环最简单的方法是什么?
for i in range(10): #or range(4, 10, 2) etc
foo(i)
我指的是像这样简单的一行
for(auto i: range(10)) //or range(4, 10, 2) or range(0.5, 1.0, 0.1) etc
foo(i);
但不像这样:
std::vector<int> v(10);
std::iota(begin(v), end(v), 0);
for(auto i: v) {
foo(i);
}
或
for(auto i: []{vector<size_t> v(10); return iota(begin(v), end(v), 0), v;}() ) {
foo(i);
}
当然,使用这些例子或仅仅使用for(;;)
并不困难,但我希望有一种方法可以在python中简单明了地做到这一点。
没有提供类似python的range
概念,但您可以使用简单的迭代器滚动自己的Range
类,如下所示:
#include <iostream>
template <typename T>
class Range
{
public:
class iterator
{
public:
explicit iterator(T val, T stop, T step) : m_val(val), m_stop(stop), m_step(step) { }
iterator& operator ++ ()
{
m_val += m_step;
if ((m_step > 0 && m_val >= m_stop) ||
(m_step < 0 && m_val <= m_stop))
{
m_val = m_stop;
}
return *this;
}
iterator operator ++ (int) { iterator retval = *this; ++(*this); return retval; }
bool operator == (iterator other) const {return m_val == other.m_val;}
bool operator != (iterator other) const {return !(*this == other);}
T operator * () const { return m_val; }
private:
T m_val, m_stop, m_step;
};
explicit Range(T stop)
: m_start(0), m_stop(stop), m_step(1)
{ }
explicit Range(T start, T stop, T step = 1)
: m_start(start), m_stop(stop), m_step(step)
{ }
iterator begin() const { return iterator(m_start, m_stop, m_step); }
iterator end() const { return iterator(m_stop, m_stop, m_step); }
private:
T m_start, m_stop, m_step;
};
template <typename T>
Range<T> range(T stop) { return Range<T>(stop); }
template <typename T>
Range<T> range(T start, T stop, T step = 1) { return Range<T>(start, stop, step); }
int main()
{
for (auto i : range(10)) { std::cout << " " << i; }
std::cout << std::endl;
for (auto i : range(4, 10, 2)) { std::cout << " " << i; }
std::cout << std::endl;
for (auto i : range(0.5, 1.0, 0.1)) { std::cout << " " << i; }
std::cout << std::endl;
}
为了支持基于范围的for
,迭代器类型和begin()
/end()
函数将完成这项工作。(当然,我上面的实现又快又脏,可能还可以改进。)
您将无法像这样滚动自己的类,但是一旦有了它,其用法与Python方法非常相似:
for (auto i : range(stop)) { ... }
for (auto i : range(start, stop, step)) { ... }
示例输出(请参阅此处的实时版本):
$ g++ -std=c++11 -o test test.cpp && ./test
0 1 2 3 4 5 6 7 8 9
4 6 8
0.5 0.6 0.7 0.8 0.9 1
如果您只需要整数范围,您也可以使用boost::irange
(感谢Yakk的提醒)。
相关文章:
- 为什么我的变量存在于其范围之外
- set_intersection范围范围
- 满足标准::范围::范围概念
- 向量向量的范围范围
- C++参数类型以接受适用于基于范围的 for 循环的所有序列
- 代码具有特定于函数的变量,用于更改范围之外的值
- 将自适应阈值应用于范围函数 opencv c++
- 用辅助方法范围范围的问题来操纵字符串
- C++:将参数应用于函数范围
- C++11:用容器参数定义函数(类似于基于范围的)
- 在C /STL中,是否有相当于Python范围()的紧凑型
- 用于循环范围范围
- 如何制作增强多指数复合范围语句,等效于x和y
- std::copy_n 是否适用于重叠范围?
- 依赖于模板参数的范围查找
- 标准算法 any_of()、all_of() 和 none_of() 应用于空范围
- 常数,但仅适用于此范围的剩余部分
- 确定谓词是否适用于一个范围的全部、部分或全部元素
- 延长临时的生命周期,适用于块范围的聚合,但不是通过"新";为什么?
- 矢量超出范围/范围检查