2009年10月30日 星期五

開根號

 
算平方根:
inline float sqrt (register float f)
{
    _asm {
        fld f
        fsqrt
        fstp f
    }
    return f;
}

算任意方根:
用 Newton-Raphson 求 root:
將 y = x 的 n 次方
化成 f(r) = r^n - y , r = 初始預測值
令逼近根 r' = r+e,取 Taylor Expansion:

        0 = f (r+e) = f (r) + e*f'(r) + e*e*f"(r)/2 + ...
        0 = f'(r+e) = f'(r) + e*f"(r) + ...

用前兩項來預測:

        f(r) + e*f'(r) = 0
        e = -f(r)/f'(r)

得出新的根
     
        r' = r - f(r)/f'(r)  
寫成 code 便是:
double root (double m, double n)
{      
    for (double x,d,r=m, e=1; e>5e-6; m-=e=(d*m-r)/(n*d))      
        for (d=m, x=1; x<n-1; ++x) d*=m;
    return m;
}

int main (/* daviddr 081225 */)
{
     float x, n;
     scanf ("%f %f", &x, &n);         
     printf ("%f\n", root (x,n));
}

沒有留言:

張貼留言