繁体   English   中英

SciPy:solve_bvp 问题二阶差异。 等式

[英]SciPy: solve_bvp Problem 2nd Order Diff. Eq

试图解决二阶差异。 等式有 2 个边界条件,我尝试什么都没有,我找不到一个教程,其中包含我表达中的所有/相似术语,至少对我来说,scipy 文档并没有真正解释如何使用solve_bvp 清楚。

我有等式:y'' + 2/r * y' = A * y + b * y^3 其中 y 是 r 的函数。

我把它改写如下:

y1 = y(r)

y2 = y1'

y2' = -2/r * y2 + y1(A + b * y1^2)

y'(0) = 0, y(r=10) = 常数

A、b 和常数是已知的。

我有以下代码,但它似乎不起作用,如上所述,我对文档有些困惑,因此将不胜感激!

def fun(x, y):
    return np.vstack((y[2], -2/x*y[1]+y[0]*(A+b*y[0]*y[0])))

def bc(ya, yb):
    return np.array([ya[2], yb[1]-constant])


x = np.linspace(1, 10, 10)
ya = np.zeros((3, x.size))
yb = np.zeros((3, x.size))

sol_1 = solve_bvp(fun, bc, x, ya)
sol_2 = solve_bvp(fun, bc, x, yb)

谢谢!

==========编辑======================== 有一个解析解,我已经计算过,它是只是看看我是否也能在数值上找到相同的解决方案,我认为主要问题是解决方案有两个独立的区域,一个是 r < R (in),一个是 r > R (out)。 这导致两种不同的解决方案(仅在各自的域中有效),条件是 y_in(R) == y_out(R) 和 y_in'(R) == y_out'(R)。 完整的 2 部分解决方案,其中半径 = 1,a=99,b = 1 且常数 = 1,y(inf) = 常数

从 Lutz Lehmann 的解决方案中,它得到了正确的形状(至少对于内部区域,虽然不是在正确的尺度上)。

我只是不确定您将如何编写所有等价解决方案,我想甚至首先要获得他们的解决方案,尽管 Lutz 的回答是正确方向上的一个惊人点。 谢谢

问题

  • 方程的阶数为 2,因此状态向量的维数为 2,值始终为y[0] ,导数y[1] ,没有y[2] ,可能是 Matlab 翻译的残余.

  • 同样在边界条件中,没有ya[2] ,导数值为ya[1] ,第二个中的函数值为yb[0]

  • 初始解猜测必须具有相同数量的 2 状态分量。

  • 为什么用相同的数据计算两个解决方案?

  • 备注:没有必要将返回值转换为 numpy 类型,求解器无论如何都会检查和转换。

具有奇异性处理的 BVP 框架

ODE 在r=0处是奇异的,因此必须以特殊方式处理第一段。 均值定理给出

(y'(r)-y'(0))/r->y''(0)  for  r->0,

所以在那个极限r->0你得到

3*y''(0) = a*y(0) + b*y(0)^3`. 

这允许将第一条弧定义为

y(r) = y0 + (a*y0 + b*y0^3)*r^2/6
y'(r) = (a*y0 + b*y0^3)*r/3

最多订购 因此,如果您希望y(r)精度为1e-9 ,则第一段不应长于1e-3

不要试图从y(h)y'(h)的方程中消除y0以获得连接ya[0]ya[1] ,而是让求解器也做这项工作并将y0作为参数添加到系统中. 那么边界条件有 3 个槽对应于为参数添加的虚拟维度,可以自然地用方程y(h)=ya[0]ya[1]=y'(h)和右边界条件填充.

总而言之,您可以将系统定义为

h = 1e-3;

def fun(r, y, p):
    return  y[1], -2/r*y[1]+y[0]*(a+b*y[0]*y[0]) 

def bc(ya, yb, p):
    y0, = p
    yh = y0 + y0*(a+b*y0*y0)*h*h/6;
    dyh = y0*(a+b*y0*y0)*h/3
    return ya[0]-yh, ya[1]-dyh, yb[0]-c


x = np.linspace(h, 10, 10)
ya = np.zeros((2, x.size))

sol = solve_bvp(fun, bc, x, ya, p=[1])
print(sol.message,f"y(0)={sol.p[0]}");
plt.plot(sol.x, sol.y[0]);

以便使用示例参数a, b, c = -1, 0.2, 3你会得到一个收敛求解器调用y(0)=2.236081087849196和结果图

在此处输入图片说明

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM