Python newton raphson;计算精度

时间:2018-02-19 13:40:16

标签: python newtons-method

我在python中编写了这个函数:

def f2(x):
    return (5.0*x + log1p(x) - 10000.0)

def dfdx2(x):
    return (5.0-(1.0/x))

def newtonRaphson2(f, dfdx, x, tol):

    x0 = x

    for i in range(1, 2000):
        if f(x) == 0.0:
            return x

    if dfdx(x) == 0.0:
        print(dfdx(x))
        break

    x = x - (f(x) / dfdx(x))
    #print(x)

    Er = abs(x0-x)/abs(x0)
    if Er <= tol:
        return x
    print(Er)
    x0 = x
    return x

然后我这样执行:

task2 = newtonRaphson2(f2, dfdx2, 1, 0.000001);
print(task2)

对于输出检查,Er在返回x之前输出4.245665128208564e-05的最终精度。

X在1998.479871524306返回,这是一个非常好的估计,但我最好还是希望至少降到1.0e-06。将tol变量更改为1.0e-08似乎什么都不做。

我猜可能把每个变量都放到一个更好的想法,但我仍然不知道为什么我的代码停在它的位置。我也不是那么稳定的python,这就是我要问的原因。我已经写过其中一个有效,但它是一个更简单的方程式。

2 个答案:

答案 0 :(得分:0)

正如@ alex-dubrovsky所指出的那样,暗示收敛的计算应该用条件循环来实现,即:

while True:
    if f(x) == 0.0:
        return x

    if dfdx(x) == 0.0:
        print(dfdx(x))
        break

    x = x - (f(x) / dfdx(x))
    #print(x)

    Er = abs(x0-x)/abs(x0)
    if Er <= tol:
        return x
    print(Er)
    x0 = x

使用这种方法你总是处于无限循环的风险之中,但这或多或少都很好,因为算法意味着“直到收敛”

答案 1 :(得分:0)

您的代码正常工作,一旦您正确缩进并添加from math import log1p。只需将print(Er)行放在计算后即可查看其最终值。 Er转到~10^-9。这对我有用:

from math import log1p

def f2(x):
    return (5.0*x + log1p(x) - 10000.0)

def dfdx2(x):
    return (5.0-(1.0/x))

def newtonRaphson2(f, dfdx, x, tol):

    x0 = x
    for i in range(1, 2000):
        if f(x) == 0.0:
            return x

        if dfdx(x) == 0.0:
            print(dfdx(x))
            break
        x = x - (f(x) / dfdx(x))
        #print(x)

        Er = abs(x0-x)/abs(x0)
        print('Er = {}'.format(Er))
        if Er <= tol:
            return x

        x0 = x
    return x

x = newtonRaphson2(f2, dfdx2, 1, 0.0000001)
print 'X = {}'.format(x)

输出结果为:

Er = 2498.5767132
Er = 0.200506616666
Er = 4.24566512821e-05
Er = 8.49642413214e-09
X = 1998.47987152

请考虑在此使用while。 Newton-Raphson算法通常收敛速度非常快,因此大多数情况下都不需要多次迭代。

这给出了相同的结果:

    from math import log1p

def f2(x):
    return (5.0*x + log1p(x) - 10000.0)

def dfdx2(x):
    return (5.0-(1.0/x))

def newtonRaphson2(f, dfdx, x, tol):

    x0 = x
    Er = 1
    while Er >= tol:
        if f(x) == 0.0:
            return x

        if dfdx(x) == 0.0:
            print(dfdx(x))
            break
        x = x - (f(x) / dfdx(x))
        #print(x)

        Er = abs(x0-x)/abs(x0)
        print('Er = {}'.format(Er))

        x0 = x
    return x

x = newtonRaphson2(f2, dfdx2, 1, 0.0000001)
print 'X = {}'.format(x)