访问结构时如何避免分配?朱莉亚

时间:2019-03-30 09:03:16

标签: memory-management julia

我正在尝试使函数调用具有尽可能少的内存分配,以使其运行更快。问题是,当我访问作为参数给出的结构时,似乎有很多分配。

function mCondition(y,t,integrator)
    xp, yp, zp, vx, vy, vz = y
    mu = integrator.p[1]
    cond = (xp - 1.0 + mu)*vx +  yp*vy + zp*vz
    return cond
end
struct myStr
    p
    u
end

y = rand(6)
t = 0.0
A = myStr([0.01215],rand(6))

#test call
mCondition(y,t,A)

using BenchmarkTools
@btime mCondition(y,t,A)

输出为:

julia> @btime mCondition(y,t,A)
  102.757 ns (9 allocations: 144 bytes)
-0.07935578340713843

我认为问题出在结构上,因为当我删除那部分代码时,

function mCondition(y,t,integrator)
    xp, yp, zp, vx, vy, vz = y
    cond = (xp - 1.0)*vx +  yp*vy + zp*vz
    return cond
end

这是基准测试的结果:

julia> @btime mCondition(y,t,A)
  18.294 ns (1 allocation: 16 bytes)
-0.08427348469961408

与函数内部发生的事情更接近我的预期(但是我仍然想知道是否甚至需要这种分配)。如果您可以帮助我了解正在发生的事情,甚至可以修复它,那将是很好的。

预先感谢:)

1 个答案:

答案 0 :(得分:-1)

您需要在struct中键入注释字段定义,以使编译器能够生成高性能代码。在struct字段中没有类型注释的情况下,编译器无法在编译时推断字段的类型,这会将决策留给运行时,因此会损害性能并导致不必要的分配。

那么解决方法是

struct myStr
    p::Vector{Float64}
    u::Vector{Float64}
end

例如,如果您希望struct与其他类型的Vector一起使用,则可以对其进行参数化。有关更多信息,请参见文档的Performance Tips部分。

我还建议您阅读文档的{{3}}部分,以详细了解如何在Julia中编写高性能代码。