Newton迭代法求平方根
牛顿迭代法求根 (即曲线与x坐标轴交点) :
在曲线的一点P1(a, f(a)), 做切线,
切线与x轴, 相交于 A 点,
A点做垂线
与曲线交于 P2(b, f(b)) 点,
在P2点继续做切线,
切线与x轴, 相交于 B 点,
...
重复此步骤, 与x轴的交点, A, B, ... 会趋近于曲线的根。
正在学习go, go语言实现版, 求2的平方根:
package main import ( "fmt" "math" ) const STEP_CNT = 10 func sqrt(x float64) float64 { ft, t := 1.0, 1.0 for i := 0; i < STEP_CNT; i++ { t = ft ft = t - (t * t -x) / 2 / t fmt.Println("step: ", i, ft) } return ft } func main() { fmt.Println(sqrt(2)) fmt.Println(math.Sqrt(2)) }
曲线上选一点 P1(t, f(t)), 本例中 曲线方程为 y = x2 - 2, 因此f(t) = t2 - 2
P1切线方程为 y = f(t) + k(x - t), 斜率k 为2t, 因此 y = f(t) + k (x - t)
切线与x轴交点, 即f(t) + k(x - t) = 0 => x = t - f(t)/k
因此迭代为 : tn+1 = tn - f(tn)/k , 其中 f(t) = t2 - 2,k = 2t
因此 tn+1 = tn - (tn * tn - 2) / 2tn
代码中 ft = t - (t * t - x ) / 2 / t 即由此得来。
扩展打到求高次幂。
tn+1 = tn - f(tn)/k, f(t) = tp - value, 求value的 p 次根
f'(t) = p * tp-1
代码如下:
package main import ( "fmt" "math" ) const STEP_CNT = 10 func sqrt(x float64, n int) float64 { if n < 2 { return 0 } ft, t := 1.0, 1.0 for i := 0; i < STEP_CNT; i++ { t = ft k := float64(n) * math.Pow(t, float64(n - 1)) f_current := math.Pow(t, float64(n)) ft = t - (f_current - x) / k fmt.Println("step: ", i, ft) } return ft } func main() { fmt.Println(sqrt(81, 4)) fmt.Println(sqrt(27, 3)) fmt.Println(sqrt(9, 2)) }