自定义函数局部极值求解:驻点位置、值及性质判定需求
如何找到二元函数的驻点并判断极值
看起来你已经在Mathematica里尝试找这个二元函数的驻点了,我来帮你梳理清楚完整的步骤,包括驻点定位、函数值计算以及极值判断,另外也补充Python的实现方案,方便你对比参考~
先看一下目标函数:
import numpy as np def func(x,y): return (np.cos(x*10))**2 + (np.sin(y*10))**2
这是一个分离变量的二元函数,x和y的部分相互独立,所以我们可以分别找到x、y方向的临界点,再组合得到所有驻点,这样计算会更简单。
一、Mathematica 实现步骤
1. 定义函数并求一阶偏导
首先在Mathematica里定义函数,然后计算对x和y的一阶偏导数:
(* 定义目标函数 *) f[x_, y_] := Cos[10 x]^2 + Sin[10 y]^2 (* 计算一阶偏导数 *) firstDerivX = D[f[x, y], x] (* 结果:-20 Cos[10 x] Sin[10 x] → 化简为 -10 Sin[20 x] *) firstDerivY = D[f[x, y], y] (* 结果:20 Sin[10 y] Cos[10 y] → 化简为 10 Sin[20 y] *)
2. 解一阶偏导为0的方程组
令两个偏导数等于0,解出所有临界点的通解:
(* 解驻点方程组 *) criticalPoints = Solve[{firstDerivX == 0, firstDerivY == 0}, {x, y}]
得到的通解为:
- x = πk/20(k为任意整数)
- y = πm/20(m为任意整数)
3. 计算驻点的函数值
将通解代入原函数,根据k、m的奇偶性,函数值有三种情况:
- 当k为奇数、m为偶数:
Cos[10x]平方为0,Sin[10y]平方为0 → 函数值=0 - 当k为偶数、m为奇数:
Cos[10x]平方为1,Sin[10y]平方为1 → 函数值=2 - 当k、m同奇偶:
Cos[10x]平方与Sin[10y]平方一个为1一个为0 → 函数值=1
4. 用海森矩阵判断极值类型
计算二阶偏导构建海森矩阵,通过行列式和二阶偏导的符号判断极值:
(* 计算二阶偏导数 *) secondDerivXX = D[f[x, y], {x, 2}] (* 结果:-200 Cos[20 x] *) secondDerivYY = D[f[x, y], {y, 2}] (* 结果:200 Cos[20 y] *) secondDerivXY = D[f[x, y], x, y] (* 结果:0,混合偏导为0 *) (* 海森矩阵行列式 *) hessianDet = secondDerivXX * secondDerivYY - secondDerivXY^2
代入驻点的x、y值(20x=kπ,20y=mπ),得到:
Cos[20x] = Cos[kπ] = (-1)^k,Cos[20y] = Cos[mπ] = (-1)^m- 行列式
hessianDet = -40000*(-1)^k*(-1)^m = -40000*(-1)^(k+m)
根据行列式判断:
- 行列式>0:是极值点。若
secondDerivXX>0则为极小值点,否则为极大值点- 当k奇、m偶:行列式=40000>0,
secondDerivXX=200>0→ 极小值点(函数值0) - 当k偶、m奇:行列式=40000>0,
secondDerivXX=-200<0→ 极大值点(函数值2)
- 当k奇、m偶:行列式=40000>0,
- 行列式<0:是鞍点(函数值1)
- 当k、m同奇偶时,行列式=-40000<0 → 鞍点
完整Mathematica示例代码
(* 定义函数 *) f[x_, y_] := Cos[10 x]^2 + Sin[10 y]^2 (* 求一阶偏导并解驻点 *) firstDerivX = D[f[x, y], x]; firstDerivY = D[f[x, y], y]; criticalPoints = Solve[{firstDerivX == 0, firstDerivY == 0}, {x, y}]; (* 计算二阶偏导和海森行列式 *) secondDerivXX = D[f[x, y], {x, 2}]; secondDerivYY = D[f[x, y], {y, 2}]; hessianDet = secondDerivXX * secondDerivYY; (* 定义驻点分类函数 *) classifyPoint[k_, m_] := Module[{x0, y0, fVal, det, xx}, x0 = Pi*k/20; y0 = Pi*m/20; fVal = f[x0, y0]; det = hessianDet /. {x -> x0, y -> y0}; xx = secondDerivXX /. {x -> x0, y -> y0}; Which[ det > 0 && xx > 0, "极小值点", det > 0 && xx < 0, "极大值点", det < 0, "鞍点" ] ]; (* 测试几个驻点 *) Print["k=0, m=1: ", classifyPoint[0, 1], ",函数值: ", f[0, Pi/20]]; Print["k=1, m=0: ", classifyPoint[1, 0], ",函数值: ", f[Pi/20, 0]]; Print["k=0, m=0: ", classifyPoint[0, 0], ",函数值: ", f[0, 0]];
二、Python 实现方案
因为函数是分离变量的,我们可以遍历整数k、m来生成驻点,再判断极值:
import numpy as np def func(x, y): return (np.cos(x*10))**2 + (np.sin(y*10))**2 def get_critical_points(k_min, k_max, m_min, m_max): """生成指定范围内的驻点列表,包含位置、函数值、极值类型""" critical_list = [] for k in range(k_min, k_max+1): x = k * np.pi / 20 for m in range(m_min, m_max+1): y = m * np.pi / 20 f_val = func(x, y) # 计算二阶偏导和海森行列式 dxx = -200 * np.cos(20 * x) dyy = 200 * np.cos(20 * y) det_hessian = dxx * dyy # 判断极值类型 if det_hessian > 0: if dxx > 0: point_type = "极小值点" else: point_type = "极大值点" elif det_hessian < 0: point_type = "鞍点" else: point_type = "无法直接判断" critical_list.append({ "位置": (round(x, 4), round(y, 4)), "函数值": round(f_val, 4), "类型": point_type }) return critical_list # 示例:生成k从0到3,m从0到3的驻点 points = get_critical_points(0, 3, 0, 3) for idx, point in enumerate(points, 1): print(f"驻点{idx}: 位置{point['位置']},函数值{point['函数值']},类型{point['类型']}")
运行上述代码后,你会得到指定范围内所有驻点的详细信息,包括位置、函数值和极值类型。
内容的提问来源于stack exchange,提问作者SuperCiocia
相关产品推荐
相关产品推荐

