我正在使用 Julia 解决以下颂歌。我使用的代码如下:
using DelimitedFiles
using LinearAlgebra
using Random
using Distributions
using DifferentialEquations
using Plots
N = 100
σ, a, J, K = 10.0, 1.0,1.0,1.0
ω = zeros(N);
function heaviside(x::Real)
return x >= 0.0 ? 1.0 : 0.0
end
function rhs(du,u,p,t)
u1 = @view u[1:N]
du1 = @view du[1:N]
u2 = @view u[N+1:2*N]
du2 = @view du[N+1:2*N]
σ,a,J,K=p
for i in 1:N
du1[i]=(1/N)*sum(j->((u1[j]-u1[i])*(1+J*cos(u2[j]-u2[i]))-sign(u1[j]-u1[i])),1:N)
du2[i]=(ω[i]) + (K/N)* sum(j->(sin(u2[j]-u2[i])*(1-(u1[j]-u1[i])^2/
σ^2)*heaviside(σ - abs((u1[j]-u1[i])))),1:N)
end
return du
end
ti=0
tf=500
tt=0.75*tf
tspan = (ti, tf) # Assuming you want to integrate from 0 to T
dts=0.25
vector_t=tt:dts:tf
p=[σ,a,J,K]
Random.seed!(123)
u0= [(rand() * 8.0 - 4.0, rand() * (2.0 * π) - π) for j in 1:N]
u0=vcat([x[1] for x in u0], [x[2] for x in u0]);
prob = ODEProblem(rhs,u0, tspan,p);
# For making mean_u1 zero
function condition(u,t,integrator)
t == integrator.t
end
function affect!(integrator)
u1_mean = mean(integrator.u[1:N])
integrator.u[1:N] .-= u1_mean
end
cbd = DiscreteCallback(condition, affect!)
##################################
saved_values2= SavedValues(Float64,ComplexF64)
function saver2(u,t,integrator)
_pp=u[1:N]
_qq=u[N+1:2*N]
out2= mean((_pp).*exp.((_qq)*1im))
end
cb2 = SavingCallback(saver2, saved_values2,saveat=tt:dts:tf)
###################################
###################################
saved_values4= SavedValues(Float64,Float64)
function saver4(u,t,integrator)
duc=rhs(zeros(size(u)),u,integrator.p,t)
_pp=duc[1:N]
_qq=duc[N+1:2*N]
out4= mean(sqrt.(((_pp).^2)+((_qq).^2)))
end
cb4 = SavingCallback(saver4, saved_values4,saveat=tt:dts:tf)
#####################################
cbs = CallbackSet(cbd, cb2,cb4);
@time sol= solve(prob, Tsit5(),reltol=1e-6,maxiters=1e20, callback = cbs,saveat=
[tf]);
sizeof(sol)
saved_values4.saveval
print(mean(saved_values4.saveval));
Z1=saved_values2.saveval;
vel=saved_values4.saveval;
因此,在上面的代码中,我使用 DiscreteCallback 在每个积分步骤后将 u1 变量的平均值设为零,然后使用 SavingCallback 来存储时间范围 tt:dts:tf 内积分的两个测量值 Z1 和 vel,因此在 SavingCallback 函数中,我添加了 saveat=tt:dts:tf。 所以,我不需要积分后sol给出的整个解,只需要最后一次的解。这就是为什么我在那里使用了 saveat=[tf] 。但即使在执行此操作之后,集成也会保存所有步骤的解决方案。那么任何人都可以建议我为什么会发生这种情况以及如何克服这个问题,因为节省溶胶占用大量空间并使我的机器非常慢。
请仅发布最少的、可重现的示例,请参阅 https://stackoverflow.com/help/minimal-reproducible-example 获取解释。
关于你的问题,当你希望
SavingCallback
仅在最后一个时间步保存时,那么你也必须仅在 saveat
的 SavingCallback
使用最后一个时间步,而不是(仅) solve
命令。目前,您向 SavingCallback
提供了保存在 tt:dts:tf
的说明