出于验证的目的,我希望能够计算出由于在某些特定算术计算期间舍入到可表示值而导致的累积误差的合理严格上限。
假设我们有一个foo()
声称执行某些特定算术计算的函数。还假设存在关于最大误差(由于舍入)的隐含保证,该保证源于所涉及的类型是float
ordouble
以及执行计算的隐含(或陈述)方式foo()
。
我希望能够通过以foo()
跟踪累积的最坏情况错误的方式执行计算来验证一组特定输入值的结果,然后检查两个结果是否与最终结果一样接近最坏情况下的错误要求。
我想可以通过引入一个新的算术类来做到这一点,该类track_prec<T>
将精度跟踪添加到基本浮点类型之一,然后让该类的算术运算符的实现来计算最差的- 每个子表达式的大小写错误。我的问题是我不知道如何在这些一般情况下计算这些最坏情况错误:
// T = float or double
template<class T> class track_prec {
public:
T value;
T ulp; // http://en.wikipedia.org/wiki/Unit_in_the_last_place
track_prec& operator+=(const track_prec& v)
{
value += v.value;
ulp = ???; // How to do this? And what about -=, *=, and /=?
}
friend bool operator==(T, const track_prec&)
{
// Exactly how should this comparison be done?
}
};
例如,假设这foo()
是对一系列数字的简单求和。然后我们可以使用track_prec<T>
如下:
std::vector<T> values { 0.4, -1.78, 1.3E4, -9.29E3, ... };
CHECK_EQUAL(std::accumulate(values.begin(), values.end(), track_prec<T>()),
foo(values.begin(), values.end()));
当然,任何形式的帮助都是受欢迎的,但是指向免费和工作代码的指针会非常好。
我找到了有关该主题的这些链接,但它们似乎没有直接回答我的问题。