首页 > 解决方案 > Python odeint with array in differential equation

问题描述

I have next first order differential equation (example):

dn/dt=A*n; n(0)=28

When A is constant, it is perfectly solved with python odeint. But i have an array of different values of A from .txt file [not function,just an array of values]

A = [0.1,0.2,0.3,-0.4,0.7,...,0.0028]

And i want that in each iteration (or in each moment of time t) of solving ode A is a new value from array. I mean that: First iteration (or t=0) - A=0.1 Second iteration (or t=1) - A=0.2 and etc from array.

How can i do it with using python odeint?

标签: pythonodeodeint

解决方案


是的,你可以这样做,但不能直接在 中odeint,因为它没有事件机制,你提出的需要一个事件动作机制。

但是你可以将你的问题分成几个步骤,在每个步骤odeint中使用现在的常量A参数,然后最后加入这些步骤。

T = [[0]]
N = [[n0]]
for k in range(len(A)):
    t = np.linspan(k,k+1,11);
    n = odeint(lambda u,t: A[k]*u, [n0],t)
    n0 = n[-1]
    T.append(t[1:])
    N.append(n[1:])

T = np.concatenate(T)
N = np.concatenate(N)

如果您对 ODE 的评估和内部步骤数的效率较低感到满意,您还可以将参数实现为分段常数函数。

tA = np.arange(len(A));
A_func = interp1d(tA, A, kind="zero", fill_value="extrapolate")
T = np.linspace(0,len(A)+1, 10*len(A)+11);
N = odeint(lambda u,t: A_func(t)*u, [n0], T)

内部步长控制器的工作假设 ODE 函数可以很好地微分到 5 阶或更高阶。然后通过步进误差计算中固有的隐式数值微分将跳跃视为高度振荡的事件,需要非常小的步长。代码内部有一些缓解措施,通常允许求解器最终跨过这样的跳转,但与上面的第一个变体相比,它需要更多的内部步骤,因此需要更多的函数评估。


推荐阅读