(演習として) C++ で単純な数値範囲クラスを作成しようとしています。等間隔の double を反復処理できます ( numpy/Python のようにarange
):
私がやりたいこと(ただし、イテレータを使用):
double lower = ..., upper = ..., delta = ...;
for (double val = lower; val < upper; val += delta)
{
// do something with val
f(val);
}
// include the last val to guarantee upper is included or exceeded
f(val); // do something with val
必要な同等の反復子コード:
double lower = ..., upper = ..., delta = ...;
NumericRange nr(lower, upper, delta);
for (NumericRange::const_iterator iter = nr.begin(); iter != nr.end(); iter++)
{
f(*iter);
}
コードを再利用できるように、イテレーターを STL イテレーターと互換性を持たせたいと考えています (NumericRange を反復することは、std::vector を反復することと同等である必要があります)。
std::vector に値を格納するだけで成功しました (そして、std::vector のイテレータを使用します)。これが、私がオンラインで見つけたすべてがこの問題を解決した方法です。ただし、リスト全体を保存する必要はありません。
値のセット全体を保存しないようにする方法はありますか? を保存せずに目的の効果を得るために、からiterable
継承してオーバーライドできるクラスはありますか?++
==
std::vector<double>
(BOOSTなしでこれを行う方法を本当に知りたいのですが、BOOSTソリューションのようなものを(ゼロから)書く方法を学びたいので、その部分は間違いなく知っていますのソフトウェア エンジニアリングは、他の人が作成したツールを使用していますが、それらのツールがどのように設計および構築されているかを学びたいと思っています)。
私の反復可能な NumericRange クラス (std::vector<double>
内部的に使用):
class NumericRange
{
protected:
double lower, upper, delta;
std::vector<double> sorted_range;
public:
typedef std::vector<double>::const_iterator const_iterator;
NumericRange()
{
lower = upper = delta = std::numeric_limits<double>::quiet_NaN();
// vector is constructed empty
}
NumericRange(double lower_param, double upper_param, double delta_param)
{
lower = lower_param;
upper = upper_param;
delta = delta_param;
assert(upper_param > lower_param);
double val;
// note: can be much faster without push_back
for (val = lower_param; val < upper_param; val += delta_param)
{
sorted_range.push_back(val);
}
// ensure the upper_value is contained or surpassed
sorted_range.push_back(val);
}
// to prevent comparison of the entire vector
bool operator ==(const NumericRange & rhs) const
{
return lower == rhs.lower && upper == rhs.upper && delta == rhs.delta;
}
// note: this class doesn't really need to store the values in a
// vector, but it makes the iterator interface much easier.
const_iterator begin() const
{
return sorted_range.begin();
}
const_iterator end() const
{
return sorted_range.end();
}
double get_lower() const
{
return lower;
}
double get_upper() const
{
return upper;
}
double get_delta() const
{
return delta;
}
size_t size() const
{
return sorted_range.size();
}
void print() const
{
std::cout << "[ " << lower << " : " << upper << ": +=" << delta << " ]" << std::endl;
}
};