当 scipy.integrate.odeint 中的输出达到 0 时停止积分

我写了一个代码,它通过拖动来观察物体的弹丸运动。我正在使用 scipy 的 odeint 来执行前向欧拉方法。积分会一直运行,直到达到时间限制。我想在达到此限制或 ry = 0 的输出(即弹丸已着陆)时停止积分。


def f(y, t):

    # takes vector y(t) and time t and returns function y_dot = F(t,y) as a vector

    # y(t) = [vx(t), vy(t), rx(t), ry(t)]


    # magnitude of velocity calculated

    v = np.sqrt(y[0] ** 2 + y[1] **2)


    # define new drag constant k

    k = cd * rho * v * A / (2 * m)


    return [-k * y[0], -k * y[1] - g, y[0], y[1]] 



def solve_f(v0, ang, h0, tstep, tmax=1000):

    # uses the forward Euler time integration method to solve the ODE using f function

    # create vector for time steps based on args

    t = np.linspace(0, tmax, tmax / tstep)


    # convert angle from degrees to radians

    ang = ang * np.pi / 180


    return odeint(f, [v0 * np.cos(ang), v0 * np.sin(ang), 0, h0], t)


solution = solve_f(v0, ang, h0, tstep)

我已经尝试了几个循环,并尝试在 ry = 0 时停止集成。并在下面找到了这个问题,但无法使用 odeint 实现类似的功能。solution[:,3] 是 ry 的输出列。有没有一种简单的方法可以用 odeint 做到这一点?


慕容森
浏览 202回答 2
2回答

明月笑刀无情

scipy.integrate.ode 在这里结帐。它比odeint您想做的事情更灵活,并有助于您完成任务。一个使用垂直射击的简单示例,积分直到它接触地面:from scipy.integrate import ode, odeintimport scipy.constants as SPCdef f(t, y):    return [y[1], -SPC.g]v0 = 10y0 = 0r = ode(f)r.set_initial_value([y0, v0], 0)dt = 0.1while r.successful() and r.y[0] >= 0:    print('time: {:.3f}, y: {:.3f}, vy: {:.3f}'.format(r.t + dt, *r.integrate(r.t + dt)))每次调用时r.integrate,r都会存储当前时间和 y 值。如果要存储它们,可以将它们传递给列表。
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Python