1
    public static double squareRoot(double num) throws IllegalArgumentException
    {
        if (num < 0.0)
            throw new IllegalArgumentException("Number cannot be negative.");
        double guess = num / 2.0, pastGuess;
        guess = 0.5 * (guess + (num / guess));

        do {
            pastGuess = guess;
            guess = 0.5 * (guess + (num / guess));
           } while ((pastGuess / guess) >= 1.01);// run until both numbers are within 1% of each other
        return guess; // return square root of num
    }

我试图使用巴比伦算法实现一个简单的 squareRoot 方法。我的问题是,对于小于 0.01 的数字,结果非常不准确。

我希望循环运行,直到两个数字(过去的猜测和猜测)都在 1% 以内(如果彼此),但我无法弄清楚它的正确数学。

我想出了:

((pastGuess / guess) >= 1.01)   

我也试过:

((pastGuess / guess) >= 1.01 || (guess / pastGuess ) >= 1.01)  

这工作得更好,但有没有更有效的方法呢?

4

4 回答 4

5
double ratio = pastGuess / guess;
(ratio >= 1.01 || ratio <= 0.99)

请注意,我用于0.99可读性。上述验证对​​称的正确值将是一个常数,等于(100/101) = 0.99009900...

于 2013-05-15T18:53:42.710 回答
4

猜你也想要 99%,所以基本上这意味着差异小于 1%:

Math.abs((pastGuess - guess) / guess) < 0.01

这应该已经很稳定了。

干杯!

于 2013-05-15T18:53:38.793 回答
2
float parcent = Math.abs(1f - (pastGuess / guess))

if(parcent <= 0.01f) 

:D

于 2013-05-15T18:51:32.300 回答
1

假设这两个数字是“a”和“b”。假设a < b。

“b”的 1% = b/100

“a”的 1% = a/100

因此,如果 a > bb/100 或 (ba)/b < 1/100,则“a”在“b”的 1% 以内

如果 b < a+a/100 或 (ba)/a < 1/100,则“b”在“a”的 1% 以内。

因为 a< b 它意味着 (ba)/b < (ba)/a

因此,如果 (ba)/a < 1/100,则意味着 (ba)/b < 1/100,因为 (ba)/b 小于 (ba)/a。

所以检查可以是:

abs(guess-pastguess)/ ((guess < pastguess) ? guess : pastguess) < 0.01 ;

让我们看一个例子:

如果 a=99.001 且 b=100 则 b=100 不在 a=99 的 1% 范围内 99.001 的 1% 为 0.99001,因此 b 必须小于 99.99001

另一方面,b=99.0001 在 a=100 的 1% 以内,因为 100 的 1% 是 0.1。所以任何大于 99 的数字都在 100 的 1% 以内。

于 2013-05-15T20:07:57.183 回答