Julia 如何在DiscreteCallback中读取指定时间对应的值?
与之类似,我试图用一个与时间相关的输入参数来求解此ODE。它由一系列的步骤组成。在某些时候,参数会发生更改(而不是状态!)。时间和值存储在Julia 如何在DiscreteCallback中读取指定时间对应的值?,julia,differential-equations,differentialequations.jl,Julia,Differential Equations,Differentialequations.jl,与之类似,我试图用一个与时间相关的输入参数来求解此ODE。它由一系列的步骤组成。在某些时候,参数会发生更改(而不是状态!)。时间和值存储在nx2数组中。但是我无法使用impact函数在指定的时间找到相应的参数值。在给定的示例中,分配给u[1]的值通常是常量。考虑这个MWE(用一个非常类似Matlab的方法),它正确地工作,没有回调: using DifferentialEquations using Plots function odm2prod(dx, x, params, t) k
nx2数组中。但是我无法使用impact
函数在指定的时间找到相应的参数值。在给定的示例中,分配给u[1]
的值通常是常量。考虑这个MWE(用一个非常类似Matlab的方法),它正确地工作,没有回调:
using DifferentialEquations
using Plots
function odm2prod(dx, x, params, t)
k_1, f_1, V_liq, X_in, Y_in, q_in = params
rho_1 = k_1*x[1]
q_prod = 0.52*f_1*x[1]
# Differential Equations
dx[1] = q_in/V_liq*(X_in - x[1]) - rho_1
dx[2] = q_in/V_liq*(Y_in - x[2])
end
x0 = [3.15, 1.5]
tspan = (0.0, 7.0)
params = [0.22, 43, 155, 249, 58, 0]
prob = ODEProblem(odm2prod, x0, tspan, params)
input = [1.0 60; 1.1 0; 2.0 60; 2.3 0; 4.0 430; 4.05 0]
dosetimes = input[:,1]
function affect!(integrator)
ind_t = findall(integrator.t == dosetimes)
integrator.p[6] = input[ind_t, 2]
end
cb = PresetTimeCallback(dosetimes, affect!)
sol = solve(prob, Tsit5(), callback=cb, saveat=1/12)
plot(sol, vars=[1, 2])
它不起作用。错误源于第22行,因为在Julia中似乎没有定义将向量与标量进行比较,或者有一种我不知道的特殊语法
我知道这是可以使用的,但我想这只适用于连续函数,而不是离散变化!?我还没有看过插值的帮助,但我不知道如何在我的具体案例中使用它
有人能告诉我怎么让它工作吗?可能只需要几行代码。此外,我不一定要将dosetimes
作为sol.t
的一部分,除非它们一致。文档中说,您使用的findall
是错误的
findall(f::Function,A)
返回a的索引或键的向量I
,其中f(a[I])
返回true
然后,您必须考虑搜索“全部”的结果是一个列表。因为您希望它只有一个元素,所以只使用第一个元素
功能影响!(积分器)
ind\u t=findall(t->t==integrator.t,dosetimes)
积分器.p[6]=输入[ind_t[1],2]
结束
你知道情节了吗
实际上,我想用Julia的findall
模拟Matlab的ismember
函数。但是,我应该把论点放在相反的地方。。。无论如何,你的解决方案是有效的。另一种选择是使用Interpolations.jl,但是先前的
插值的必要选项是。即使第一次PresetTimeCallback
发生在初始时间点,例如tspan[1]
时,我也惊讶地看到这项工作。我正在处理一个问题,PresetTimeCallback
修改状态而不是参数。在这种情况下,回调不会在初始时间点触发。你知道这会有什么不同吗?不管怎样,如果它对某人有帮助:在第二种情况下,影响代码>修改一个状态,例如integrator.u[1]+=input[ind_t[1],2]
一个解决方案可以包括两个步骤:a)使用PresetTimeCallback(dosetimes,affect!,initialize=(c,u,t,integrator)->affect!(integrator))
(如中所述)。和b)修改影响
检查if(integrator.t in dosetimes)
,否则findall
可能会抛出错误。您好@fabern,有一段时间没有在这里查看。我在编写《朱莉娅》中的第一步,看看是否可以永久地改变。但是这个跳跃特性是我所做的建模中的一个基本方面,所以我需要一个真正的解决方案。这似乎是一个有趣的选择,因为他们的DosageRegimen
与我使用的提要非常相似。我最终会试一试的。