如何在odeint中记录变量的值?

时间:2019-03-27 17:27:57

标签: python-3.x numerical-methods odeint

我想知道是否有一种方法可以在积分函数中记录特定变量的值,而不必在函数定义中进行打印,这在很多情况下是由于预测算法所致-更正,导致比函数返回的最终向量更多或更少的值?


示例,请尝试使用以下代码:

import numpy as np
from scipy.integrate import odeint
import matplotlib.pyplot as plt


def essai(y, t):

    a = y[0]

    c1 = a
    a = c1 / a**2

    return [a]


# Solving
essai0 = [10]
t = np.linspace(0, 2000, 10)
y = odeint(essai, essai0, t)

a = y[:, 0]

# Graphs
fig, ax = plt.subplots()
ax.plot(t, a, 'k--', label='a')
legend = ax.legend(loc='lower right', shadow=True, fontsize='x-large')
legend.get_frame().set_facecolor('#FFFCCC')  # 00FFCC
plt.xlabel('x')
plt.ylabel('y')
plt.title('y vs x')
plt.show()

我想记录取决于c1的{​​{1}}的值。我该怎么办?

如果我打印,它会得到(由于pred-corr算法):

a

哪个值比我用10.0 10.001203411814794 10.00120326701222 10.002406534059283 10.00240638930896 10.031168251789499 10.03116843523562 10.059847893733858 10.059848247411573 10.088446178306066 10.088446526968276 10.178981333917179 10.1789826635142 10.26872274187664 10.268720875457465 10.251795853148066 10.251794757670828 10.324093402400061 10.324093338929458 10.395889284010963 10.395889126663482 10.467192620394076 10.467192470562162 10.60836217080531 10.608361512785885 10.747675991273601 10.747676529983982 10.885208084361661 10.88520861500753 11.021024408838219 11.021024559158226 11.15518691385528 11.15518704871583 11.389028983440005 11.389029612664437 11.618166387462095 11.618166372845774 11.842871925632974 11.842870666797078 12.063390475531826 12.0633901508557 12.279950446401756 12.279950250452782 12.492757035192547 12.492756877414479 12.790475076345272 12.79047467718475 13.081418818481728 13.081418595295522 13.366029970579808 13.366030900758636 13.644707388512776 13.644707798536366 13.917805722870085 13.917805853240296 14.185647189512732 14.185647276304193 14.448524340486092 14.44852440612534 14.849045554474056 14.849045812160185 15.239043242348172 15.239044113472564 15.619306858637934 15.619307570817467 15.990530200625596 15.990530706701604 16.353328829257094 16.35332918566708 16.70825155213741 16.708251810028536 17.055790075751844 17.055790265472186 17.52054793291328 17.520548366986496 17.97329155702487 17.97329263337524 18.414908470097206 18.41490919183692 18.84617978510828 18.846180323693773 19.26780035288661 19.26780072790131 19.68039039537204 19.680390669145883 20.084506483562638 20.084506685872917 20.63204921728682 20.632049705019547 21.165431430483114 21.16543268212929 21.685699626883885 21.685700483180575 22.193774842932424 22.193775478119036 22.69047628806277 22.69047673120133 23.176535191516802 23.1765355148269 23.652607704971896 23.652607943862492 24.296731084127696 24.296731656936466 24.92421316694978 24.924214631653445 25.536282592848192 25.536283593100098 26.134020839947766 26.134021582629195 26.718389929663125 26.718390447872228 27.290248649274574 27.290249027491374 27.8503676838429 27.85036796338048 28.60821935477876 28.608220025227006 29.346505899333515 29.346507613905608 30.066670806260635 30.066671977520553 30.769984796557875 30.769985666417984 31.457578314647648 31.457578921761066 32.13046057231114 32.13046101551341 32.78953730742519 32.789537635058444 33.68118868621462 33.68118947182226 34.54983545122736 34.549837459883506 35.39717380841791 35.397175180698845 36.22469707822626 36.224698097642104 37.033733817898586 37.03373452954837 37.82547018189015 37.82547070150822 38.60097077071101 38.60097115490064 39.65004988104156 39.650050802111195 40.67207751401193 40.67207986867377 41.669047220267416 41.66904882908885 42.64271422854618 42.64271542393563 43.594640193459966 43.59464102811222 44.52621945824691 44.52622006777859 45.43870353935591 45.438703990091476 46.67300975177773 46.673010832232926 47.87550305124021 47.87550581301012 49.04852683447106 49.04852872160157 50.194144483083306 50.19414588551954 51.3141919066777 51.31419288605143 52.41030839692969 52.41030911225109 53.48396538985435 53.483965918885744 54.9362075454971 54.93620881348237 56.35103457439806 56.35103781516747 57.73120149400896 57.731203708595864 59.07913425147381 59.07913589751868 60.39699143853227 60.39699258818307 61.68670054765226 61.68670138744394 62.94999176730058 62.949992388453296 64.65865496068966 64.65865644932029 所期望的值多得多,该值将时间间隔除以200的十分之一。

我已经考虑了很长时间这个问题,却没有找到解决这个问题的好方法,我很高兴知道如何绕过这个问题。

1 个答案:

答案 0 :(得分:1)

内部求解器步骤中的ODE函数的评估点与输出的解决方案所要求的采样点之间没有关系。此外,评估点可能会以比集成方法的阶次低的阶次误差偏离求解轨迹。

以结构化方式执行所需操作的最简单方法是将c1函数定义为一个单独的函数,然后在结果中调用它

def c1_func(y): return y[0]

def essai(y, t):

    a = y[0]

    c1 = c1_func(y)
    a = c1 / a**2

    return [a]

...
y = odeint(...
c1_val = c1_func(y.T)
plt.plot(x, c1_val)

等等。