基于Wolfram Mathematica的双参数绝对误差最小化技术咨询
最小化两个非线性ODE数值解的绝对误差
看起来你正在尝试最小化两个非线性常微分方程(ODE)数值解之间的绝对误差,我帮你把你的Mathematica代码整理成规范格式,同时给你一些实用的优化思路:
你的代码整理
(* 定义小参数 *) \[Epsilon] = 10^-6; (* 定义近似δ函数的尖峰函数Delta[t] *) Delta[t_] := 1/(Sqrt[\[Pi]] \[Epsilon]) Exp[-(t/\[Epsilon])^2] (* 定义驱动函数f(t) *) f[t_] := 1/2 (1 + Tanh[100 t]) (* 求解第一个ODE,得到w(t)的数值解 *) solw = NDSolve[ {w''[t] + (w[t] + w[t]^2) w'[t] == f[t], w[0] == 0, w'[0] == 0}, w, {t, 0, 2 \[Pi]}, Method -> "MethodOfLines" ]; wsol[t_] := Evaluate[w[t] /. solw] (* 补全参数与时间区间的第二个ParametricNDSolve *) solG = ParametricNDSolve[ {G''[t] + (G[t] + G[t]^2) G'[t] == s2 Delta[t], G[0] == 0, G'[0] == 0}, G, {t, 0, 2 \[Pi]}, s2 ];
误差最小化的实现思路
- 明确参数化求解:上面已经帮你补全了
ParametricNDSolve的参数s2和时间区间,这样可以生成随s2变化的解G[s2][t] - 定义误差函数:你可以选择积分形式的绝对误差,或者区间内的最大绝对误差,示例如下:
(* 积分形式的绝对误差 *) error[s2_] := NIntegrate[Abs[wsol[t] - G[s2][t]], {t, 0, 2 \[Pi]}] (* 区间内的最大绝对误差 *) maxError[s2_] := MaxValue[Abs[wsol[t] - G[s2][t]], {t, 0, 2 \[Pi]}] - 执行最小化求解:用
FindMinimum寻找使误差最小的s2值,初始猜测可以根据问题经验设置:(* 以初始猜测s2=1为例,寻找最小误差对应的参数值 *) minResult = FindMinimum[error[s2], {s2, 1}] - 优化数值求解精度:因为
\[Epsilon] = 1e-6,Delta[t]是极窄的尖峰,属于刚性问题,建议切换到刚性求解方法并提高精度:solw = NDSolve[ {w''[t] + (w[t] + w[t]^2) w'[t] == f[t], w[0] == 0, w'[0] == 0}, w, {t, 0, 2 \[Pi]}, Method -> "StiffnessSwitching", PrecisionGoal -> 8, AccuracyGoal -> 8 ]; solG = ParametricNDSolve[ {G''[t] + (G[t] + G[t]^2) G'[t] == s2 Delta[t], G[0] == 0, G'[0] == 0}, G, {t, 0, 2 \[Pi]}, s2, Method -> "StiffnessSwitching", PrecisionGoal -> 8, AccuracyGoal -> 8 ];
内容的提问来源于stack exchange,提问作者Asatur Khurshudyan
相关产品推荐
相关产品推荐

