我有多种方法用于基于以下数据类型以固定精度数字累加数量:
int95_t {
long long int x;
int y;
};
数字在
x
中向前计数,直到超出范围并回绕,此时 y
累加 +1(表示上溢)和 -1(表示下溢)。 (我也有浮点数相加的方法,可能会导致x
多次上溢或下溢,从而在y
中累积多次)。
该数据类型的加法或减法的方法有些涉及。
int95_t sum(const int95_t a, const int95_t b) {
int95_t result = { a.x + b.x, a.y + b.y };
result.y += (1 - (2 * (b.x < 0LL))) * ((a.x ^ result.x) < 0 && (a.x ^ b.x) >= 0LL) * 2;
return result;
}
int95_t subtract(const int95_t a, const int95_t b) {
const int95_t neg_b = { -b.x, -b.y + (2 * (b.x == LLONG_MIN)) };
return sum(a, neg_b);
}
我已经重载了此数据类型的运算符
+
、-
、+=
和 -=
,但这无助于清理我的代码,原因如下:在许多情况下我将存储的不是一个 int95_t
值数组,而是两个单独的数组long long int
和 int
值。 (原因是,在很多情况下,可以安全地忽略超级累加器y
,并且我想节省内存带宽。)因此,我有很多情况,为了将一个 int95_t 添加到另一个 int95_t这种情况,看来我还需要做:
long long int primary[8];
int secondary[8];
int95_t add_this = { 81573835283, 3816 };
for (int i = 0; i < 8; i++) {
int95_t tmp = { primary[i], secondary[i] };
tmp += add_this;
primary[i] = tmp.x;
secondary[i] = tmp.y;
}
还有什么更好的办法吗? 我希望我可以依靠任何给定的 C++ 编译器来正确解释上述情况下的类似内容,但我不确定:
for (int i = 0; i < 8; i++) {
{ primary[i], secondary[i] } += add_this;
}
感谢大家提供的任何帮助。
解决方案之一可能是使用重载算术创建一个临时对象,该对象保存对操作数组件的引用。例如:
class split
{
long long int ℞
int &ry;
public:
split(long long int &x, int &y) : rx { x }, ry { y } {}
split &operator+=(const int95_t &v)
{
// implement your += logic here with rx and ry modification
return *this;
}
};
for (int i = 0; i < 8; i++) {
split(primary[i], secondary[i]) += add_this;
}
您还可以重新使用此类来实现
int95_t
重载运算符实现,即
int95_t val = { 81573835283, 3816 };
split(val.x, val.y) += add_this;