算法学习笔记:19.牛顿迭代法——从原理到实战,涵盖 LeetCode 与考研 408 例题

牛顿迭代法(Newton's Method)是一种强大的数值计算方法,由英国数学家艾萨克・牛顿提出。它通过不断迭代逼近方程的根,具有收敛速度快、适用范围广的特点,在科学计算、工程模拟、计算机图形学等领域有着广泛应用。

牛顿迭代法核心思路

算法原理

牛顿迭代法的核心思想是用切线逼近曲线,通过迭代逐步缩小与方程根的距离。对于方程\(f(x) = 0\),其迭代公式为:

\(x_{n+1} = x_n - \frac{f(x_n)}{f'(x_n)}\)

其中:

  • \(x_n\) 是第\(n\)次迭代的近似根
  • \(f'(x_n)\) 是函数\(f(x)\)在\(x_n\)处的导数
  • \(x_{n+1}\) 是第\(n+1\)次迭代的近似根

几何意义

牛顿迭代法的几何意义是:在每一次迭代中,用函数\(f(x)\)在\(x_n\)处的切线代替曲线,将切线与\(x\)轴的交点\(x_{n+1}\)作为新的近似根。通过不断重复这一过程,近似根会快速收敛到方程的真实根。

以下是用 mermaid 绘制的牛顿迭代法几何示意图(以\(f(x) = x^2 - 2\)求解\(\sqrt{2}\)为例):

算法流程

牛顿迭代法的基本流程如下:

  1. 选择初始近似根\(x_0\)(初始值的选择对收敛速度影响较大)。
  2. 计算函数值\(f(x_n)\)和导数值\(f'(x_n)\)。
  3. 代入迭代公式计算\(x_{n+1}\)。
  4. 判断\(|x_{n+1} - x_n|\)是否小于预设精度\(\epsilon\)(如\(10^{-6}\)):
    • 若满足,则\(x_{n+1}\)即为近似根,迭代结束。
    • 若不满足,则令\(x_n = x_{n+1}\),返回步骤 2 继续迭代。

其流程可用以下流程图表示:

收敛性分析

  • 收敛条件:若函数\(f(x)\)在根的邻域内二阶可导且一阶导数不为 0,则牛顿迭代法具有局部收敛性,且收敛阶为 2(二次收敛),即误差以平方级速度减小。
  • 影响因素
    • 初始值\(x_0\)的选择:若初始值离真实根过远,可能导致迭代发散或收敛到其他根。
    • 导数为 0 的情况:若\(f'(x_n) = 0\),迭代公式无意义,需特殊处理。

LeetCode 例题实战

例题 1:69. x 的平方根(简单)

题目描述:给你一个非负整数 x ,计算并返回 x 的算术平方根。由于返回类型是整数,结果只保留整数部分,小数部分将被舍去。

示例

输入:x = 8

输出:2

解释:8 的算术平方根是 2.82842...,由于返回类型是整数,小数部分将被舍去。

解题思路:将问题转化为求方程\(f(t) = t^2 - x = 0\)的非负根,使用牛顿迭代法求解:

  1. 初始值选择:当\(x \geq 1\)时,取\(x_0 = x\);当\(x = 0\)时,直接返回 0。
  1. 迭代公式:\(f(t) = t^2 - x\),\(f'(t) = 2t\),代入迭代公式得\(t_{n+1} = \frac{1}{2}(t_n + \frac{x}{t_n})\)。
  1. 收敛判断:当\(|t_{n+1} - t_n| < 1\)时,整数部分已稳定,可停止迭代,返回\(t_{n+1}\)的整数部分。

代码实现

java 复制代码
class Solution {

    public int mySqrt(int x) {

        if (x == 0) {

            return 0;

        }

        double x0 = x; // 初始值

        double x1 = (x0 + x / x0) / 2; // 第一次迭代

        // 迭代直至精度满足要求(差值小于1)

        while (Math.abs(x1 - x0) >= 1) {

            x0 = x1;

            x1 = (x0 + x / x0) / 2;

        }

        return (int) x1;

    }

}

复杂度分析

  • 时间复杂度:\(O(\log x)\),牛顿迭代法具有二次收敛性,迭代次数与\(x\)的大小呈对数关系。
  • 空间复杂度:\(O(1)\),仅使用常数额外空间。
  • 说明:代码中使用 double 类型存储中间结果以保证精度,最后通过强制类型转换取整数部分。

例题 2:367. 有效的完全平方数(简单)

题目描述 :给定一个正整数 num ,编写一个函数,如果 num 是一个完全平方数,则返回 true ,否则返回 false 。

示例

输入:num = 16

输出:true

输入:num = 14

输出:false

解题思路:同样转化为求方程\(f(t) = t^2 - num = 0\)的根,若根为整数,则 num 是完全平方数:

  1. 用牛顿迭代法求出近似根\(t\)。
  1. 验证\(t\)的整数部分\(k\)是否满足\(k^2 = num\),若是则返回 true,否则返回 false。

代码实现

java 复制代码
class Solution {

    public boolean isPerfectSquare(int num) {

        if (num < 1) {

            return false;

        }

        if (num == 1) {

            return true;

        }

        double x0 = num;

        double x1 = (x0 + num / x0) / 2;

        // 迭代至精度足够高(差值小于1e-6)

        while (Math.abs(x1 - x0) > 1e-6) {

            x0 = x1;

            x1 = (x0 + num / x0) / 2;

        }

        int k = (int) Math.round(x1); // 四舍五入取整数

        return k * k == num;

    }

}

复杂度分析

  • 时间复杂度:\(O(\log num)\),迭代次数与 num 的大小呈对数关系。
  • 空间复杂度:\(O(1)\),仅使用常数额外空间。
  • 说明:通过四舍五入处理近似根,确保整数部分的准确性,再验证是否为完全平方数。

例题 3:50. Pow (x, n)(中等)

题目描述:实现 pow(x, n) ,即计算 x 的整数 n 次幂函数(即,\(x^n\))。

示例

输入:x = 2.00000, n = 10

输出:1024.00000

解题思路:当\(n\)为负整数时,\(x^n = 1 / x^{-n}\),因此可先处理\(n\)为非负的情况。对于\(n > 0\),可通过牛顿迭代法求指数函数,但更简单的方式是结合快速幂思想优化:

  1. 转化问题:计算\(e^{n \ln x}\)(利用指数与对数的关系\(x^n = e^{n \ln x}\))。
  1. 牛顿迭代法求指数函数:但实际中更高效的是使用快速幂(分治法),此处仅展示牛顿迭代法在指数计算中的思路。

补充说明:本题虽更适合用快速幂,但牛顿迭代法可用于求解\(e^y\)的近似值(通过求方程\(f(t) = e^t - y = 0\)的根),进而间接计算\(x^n\)。以下代码展示牛顿迭代法求\(e^y\)的思路:

java 复制代码
class Solution {

    // 计算e^y的近似值

    private double exp(double y) {

        if (y < 0) {

            return 1 / exp(-y);

        }

        double t0 = y + 1; // 初始值

        double t1 = t0 - (Math.exp(t0) - y - 1) / Math.exp(t0); // 迭代公式(针对f(t)=e^t - t - 1 - y)

        while (Math.abs(t1 - t0) > 1e-6) {

            t0 = t1;

            t1 = t0 - (Math.exp(t0) - t0 - 1 - y) / (Math.exp(t0) - 1);

        }

        return Math.exp(t1) - 1;

    }

    public double myPow(double x, int n) {

        if (n == 0) {

            return 1.0;

        }

        long N = n; // 处理n为Integer.MIN_VALUE的情况

        if (N < 0) {

            x = 1 / x;

            N = -N;

        }

        // 利用x^N = e^(N ln x)

        return exp(N * Math.log(x));

    }

}

说明:本题中牛顿迭代法并非最优解,但展示了其在超越函数计算中的应用。实际解题中,快速幂(时间复杂度\(O(\log |n|)\))更为高效。

考研 408 例题解析

例题 1:数值计算应用题(408 高频考点)

题目:用牛顿迭代法求方程\(f(x) = x^3 - 2x - 5 = 0\)在\(x_0 = 2\)附近的实根,要求迭代 3 次,并计算迭代误差。

解题步骤

  1. 确定函数与导数:\(f(x) = x^3 - 2x - 5\),\(f'(x) = 3x^2 - 2\)。
  2. 迭代公式:\(x_{n+1} = x_n - \frac{x_n^3 - 2x_n - 5}{3x_n^2 - 2}\)。
  3. 计算前 3 次迭代:
    • 第 1 次:\(x_0 = 2\),\(f(x_0) = 8 - 4 - 5 = -1\),\(f'(x_0) = 12 - 2 = 10\),\(x_1 = 2 - (-1)/10 = 2.1\)。
    • 第 2 次:\(f(x_1) = 2.1^3 - 2*2.1 - 5 ≈ 9.261 - 4.2 - 5 = 0.061\),\(f'(x_1) ≈ 3*(2.1)^2 - 2 ≈ 13.23 - 2 = 11.23\),\(x_2 ≈ 2.1 - 0.061/11.23 ≈ 2.0946\)。
    • 第 3 次:\(f(x_2) ≈ (2.0946)^3 - 2*(2.0946) - 5 ≈ 0.0003\),\(f'(x_2) ≈ 3*(2.0946)^2 - 2 ≈ 11.16\),\(x_3 ≈ 2.0946 - 0.0003/11.16 ≈ 2.09455\)。
  1. 迭代误差:\(|x_3 - x_2| ≈ 0.00005\),已非常接近真实根(约 2.09455)。

答案:经过 3 次迭代,近似根为\(2.09455\),迭代误差约为\(5 \times 10^{-5}\)。

例题 2:算法分析题(选择题)

题目:关于牛顿迭代法,下列说法错误的是( )。

A. 牛顿迭代法具有二次收敛速度,收敛速度快于简单迭代法

B. 牛顿迭代法的迭代公式只与函数值和导数值有关

C. 无论初始值如何选择,牛顿迭代法都能收敛到方程的根

D. 当函数在迭代点处的导数为 0 时,牛顿迭代法无法继续迭代

答案:C

解析

  • A 正确:牛顿迭代法在满足收敛条件时为二次收敛,速度快于线性收敛的简单迭代法。
  • B 正确:迭代公式仅依赖\(f(x_n)\)和\(f'(x_n)\)。
  • C 错误:初始值选择不当可能导致迭代发散或收敛到其他根(如\(f(x) = x^3 - 3x + 1\),初始值选择不当会收敛到不同根)。
  • D 正确:若\(f'(x_n) = 0\),迭代公式分母为 0,需特殊处理(如改用其他迭代法)。

牛顿迭代法的扩展与应用

实际应用场景

  • 方程求解:求解高次方程、超越方程的根(如在物理、工程中求解运动方程)。
  • 优化问题:求函数的极值(通过求解导数为 0 的点,如机器学习中的梯度下降法可视为牛顿法的简化)。
  • 计算机图形学:求光线与物体的交点(射线追踪算法)。
  • 数值分析:计算平方根、立方根、指数函数、对数函数等。

考研 408 中的重点

在考研 408 中,牛顿迭代法的考点集中在:

  • 算法原理:理解迭代公式的推导和几何意义。
  • 收敛性分析:掌握收敛条件和影响收敛的因素。
  • 应用计算:能手动进行简单迭代计算,求解方程近似根。
  • 与其他算法的对比:如与二分法的比较(二分法收敛慢但总能收敛,牛顿法收敛快但依赖初始值)。

总结

牛顿迭代法作为一种高效的数值计算方法,凭借其二次收敛特性,在科学与工程领域有着广泛应用。本文通过 LeetCode 例题(平方根、完全平方数、指数计算)展示了其在编程中的应用,通过考研 408 例题梳理了理论考点与计算思路。

掌握牛顿迭代法不仅能提升解决数值问题的能力,还能深化对函数导数、收敛性等数学概念的理解。在实际应用中,需注意初始值的选择和收敛条件的判断,以避免迭代发散。

希望本文能够帮助读者更深入地理解牛顿迭代法,并在实际项目中发挥其优势。谢谢阅读!


希望这份博客能够帮助到你。如果有其他需要修改或添加的地方,请随时告诉我。

相关推荐
卷福同学4 小时前
不用服务器,不用配环境,我10分钟上线了一个AI Agent
人工智能·后端·算法
问君能有几多愁~6 小时前
C++ 数据结构复习笔记
数据结构·c++·笔记
至乐活着6 小时前
深入解析跳表SkipList:原理、实现与性能优化实战
数据结构·算法·跳表·skiplist·java实现
r_oo_ki_e_7 小时前
Java Map 集合学习笔记
java·笔记·学习
Jerry7 小时前
LeetCode 383. 赎金信
算法
ai产品老杨7 小时前
H264 H265视频分析常见问题和排查清单
人工智能·算法·音视频
Jerry8 小时前
LeetCode 454. 四数相加 II
算法
笨鸟先飞的橘猫8 小时前
skynet——sharetable学习
学习·skynet
liuyicenysabel8 小时前
大模型学习笔记 · 第八篇 · 进阶:偏好对齐与多卡训练
人工智能·笔记·学习
可编程芯片开发8 小时前
基于CPS-SPWM链式STATCOM系统在电压不平衡环境下控制策略的simulink建模与仿真
算法