有一个现代的方式来封闭一个int范围?



我来解释一下。我想用next创建一个范围为[min,max]的int变量属性:

  1. 必须支持int类型的'+'(加号)和'-'(减号)操作。
  2. 大于max的值应该循环到[min +余数]。
  3. 任何小于min的值应该循环到max -余数]。

例子:

int a in range (2,7);
a = 3;
a = a + 3; // a is 6 now
a = a + 1; // a is 7 now
a = a + 1; // a is greater than 7 so we loop to 2 a = 2
a = a - 3; // shoul be 2 - 3 = -1 but insted will be 5 (2 - 1 -> 7 - 2 -> 5)

我知道我可以用mod写出上界(又名%算子)。但是我认为代码会很难读。

或使用if语句。但是这样的话,性能就会下降。

有什么现代的方法吗?一些std::溶液?或者很酷的句法?

template<class T, T min, T max>
struct bounded_value {
static_assert(min <= max);
private:
T t;
public:
explicit operator T() const& { return t; }
explicit operator T() && { return std::move(t); }
inline static constexpr T delta = max-min;
bounded_value& operator+=( bounded_value const& o ) & {
t += o.t;
if (t >= max)
t -= delta;
else if (t < min)
t += delta;
return *this;
}
bounded_value& operator-=( bounded_value const& o ) & {
t -= o.t;
if (t >= max)
t -= delta;
else if (t < min)
t += delta;
return *this;
}
static T bound( T in ) {
if (in > max)
{
std::size_t count = (max-in)/delta;
in -= delta * count;
}
else if (in <= min)
{
std::size_t count = (min-in)/delta;
in += delta * count;
}
return in;
}
bounded_value& operator*=( bounded_value const& o ) & {
t = bound(t * o.t);
return *this;
}
bounded_value& operator/=( bounded_value const& o ) & {
t = bound(t / o.t);
return *this;
}
friend bounded_value operator+(bounded_value lhs, bounded_value const& rhs)
{
lhs += rhs;
return lhs;
}
friend bounded_value operator-(bounded_value lhs, bounded_value const& rhs)
{
lhs -= rhs;
return lhs;
}
friend bounded_value operator*(bounded_value lhs, bounded_value const& rhs)
{
lhs *= rhs;
return lhs;
}
friend bounded_value operator/(bounded_value lhs, bounded_value const& rhs)
{
lhs /= rhs;
return lhs;
}
bounded_value& operator++(){ *this += 1; return *this; }
bounded_value operator++(int){ auto tmp = *this; ++*this; return tmp;}
bounded_value& operator--(){ *this -= 1; return *this; }
bounded_value operator--(int){ auto tmp = *this; ++*this; return tmp;}
auto operator<=>(bounded_value const&) const =default;
bool operator==(bounded_value const&) const =default;
bounded_value( T in ):t( bound(std::move(in)) ) {}
bounded_value():t(min) {}
~bounded_value()=default;
bounded_value( bounded_value const& )=default;
bounded_value( bounded_value && )=default;
bounded_value& operator=( bounded_value const& )=default;
bounded_value& operator=( bounded_value && )=default;
};

这是一个快速的。

生活例子。

我应该在+-上添加std::ptrdiff_t过载,以支持bounded_value<Foo*, globalbuf+10, globalbuf+100>

注意,这是假设对有界值的操作不会超过或低于底层T

当执行+-时,最多进行两次检查,一次减法/加法,以保持其在边界内;没有分工。当执行*/时,最多执行两次检查,一次除法,一次乘法和一次加法/减法。

最新更新