【发布时间】:2011-01-08 22:40:08
【问题描述】:
我想要 C# 中双精度值的舍入方法。它需要能够将双精度值舍入为任何舍入精度值。我手头的代码如下:
public static double RoundI(double number, double roundingInterval) {
if (roundingInterval == 0.0)
{
return;
}
double intv = Math.Abs(roundingInterval);
double sign = Math.Sign(number);
double val = Math.Abs(number);
double valIntvRatio = val / intv;
double k = Math.Floor(valIntvRatio);
double m = valIntvRatio - k;
bool mGreaterThanMidPoint = ((m - 0.5) >= 1e-14) ? true : false;
bool mInMidpoint = (Math.Abs(m - 0.5) < 1e-14) ? true : false;
return (mGreaterThanMidPoint || mInMidpoint) ? sign * ((k + 1) * intv) : sign * (k * intv);
}
所以 RoundI(100, 3) 应该给出 99,而 RoundI(1.2345, 0.001) 应该给出 1.235。
问题是,RoundI(1.275, 0.01) 返回 1.27,而不是 1.28。这是因为当执行 double valIntvRatio = val/intv,即 double valIntvRatio = 1.275 / 0.01 时,它给出了 0.12749999999999。我知道这是任何编程语言中双重表示的问题。我的问题是,是否有标准代码来做这样的事情,而无需担心双精度?在这里我将容差设置为 1e-14,但这对于这个问题来说太严格了,我不知道要设置的正确容差是多少。感谢您的帮助。
【问题讨论】:
-
或许您应该考虑使用 Decimal 数据类型。
-
为什么round(100,3) 会给出99?如果您四舍五入到与 3(0 位)相同的小数位置,您将得到 100,而不是 99。
-
paxdiablo:抱歉,RoundI 的目的不是将第一个参数四舍五入到与第二个参数相同的小数位置。第二个参数是舍入间隔,舍入将第一个参数舍入到第二个参数的模式为0的closet值。
-
啊,这更有意义(而且我的回答不太有用)。对此深表歉意。