@dpsanders:
David,
In principle that is a great suggestion, but that means distilling the code to the absolute minimum. While I’m working on that, do you think anything could be read from the following?
Running
@time for j = 1:10000000
Jacobianvolume(femm, J, loc, conn, N)
end
@code_warntype Jacobianvolume(femm, J, loc, conn, N)
produces the timing info
0.297144 seconds (10.00 M allocations: 152.588 MB, 3.84% gc time)
and the listing
Variables:
#self#::FinEtools.FEMMBaseModule.#Jacobianvolume
self::FinEtools.FEMMBaseModule.FEMMBase{FinEtools.FESetModule.FESetT3,FinEtools.FEMMBaseModule.#otherdimensionunity}
J::Array{Float64,2}
loc::Array{Float64,2}
conn::Array{Int64,2}
N::Array{Float64,2}
Jac::Float64
Body:
begin
SSAValue(0) = FinEtools.FEMMBaseModule.FFlt
SSAValue(1) = $(Expr(:invoke, LambdaInfo for Jacobiansurface(::FinEtools.FEMMBaseModule.FEMMBase{FinEtools.FESetModule.FESetT3,FinEtools.FEMMBaseModule.#otherdimensionunity}, ::Array{Float64,2}, ::Array{Float64,2}, ::Array{Int64,2}, ::Array{Float64,2}), :(FinEtools.FEMMBaseModule.Jacobiansurface), :(self), :(J), :(loc), :(conn), :(N)))
Jac::Float64 = SSAValue(1)
SSAValue(2) = SSAValue(1)
return SSAValue(2)
end::Float64
Also,
function Jacobianvolume{T<:FESet2Manifold}(self::FEMMBase{T}, J::FFltMat,
loc::FFltMat, conn::FIntMat, N::FFltMat)::FFlt
@code_warntype Jacobiansurface(self, J, loc, conn, N)
Jac = Jacobiansurface(self, J, loc, conn, N)::FFlt
end
gives
Variables:
#self#::FinEtools.FEMMBaseModule.#Jacobiansurface
self::FinEtools.FEMMBaseModule.FEMMBase{FinEtools.FESetModule.FESetT3,FinEtools.FEMMBaseModule.#otherdimensionunity}
J::Array{Float64,2}
loc::Array{Float64,2}
conn::Array{Int64,2}
N::Array{Float64,2}
Jac::Float64
Body:
begin
$(Expr(:inbounds, false))
# meta: location C:\Users\Petr Krysl\Dropbox\Julia\FinEtools\src\FESetModule.jl Jacobian 227
SSAValue(0) = FinEtools.FESetModule.FFlt
$(Expr(:inbounds, true))
Jac::Float64 = (Base.box)(Base.Float64,(Base.sub_float)((Base.box)(Base.Float64,(Base.mul_float)((Base.arrayref)(J::Array{Float64,2},1,1)::Float64,(Base.arrayref)(J::Array{Float64,2},2,2)::Float64)),(Base.box)(Base.Float64,(Base.mul_float)((Base.arrayref)(J::Array{Float64,2},2,1)::Float64,(Base.arrayref)(J::Array{Float64,2},1,2)::Float64))))
$(Expr(:inbounds, :pop))
# meta: pop location
$(Expr(:inbounds, :pop))
return Jac::Float64
end::Float64
I can see the Base.box
, and I understand that can mean memory allocation. What I don’t get is why: the expression that gets boxed is @inbounds Jac = (J[1, 1]*J[2, 2] - J[2, 1]*J[1, 2])
. Clearly the compiler sees that J
is a double array, so why the boxing?
Thanks a lot.
Petr