Hey,
In my package Copulas.jl there might be a typing error somewhere that does not allow ForwardDiff to pass through some of the functions. Symply trying to minimize the loglikelyhood of the model does not work as expected :
EDIT: You need Copulas.jl#master
to see the bug for the moment.
using Copulas, Distributions, Random, ForwardDiff#, Turing, Plots, Cthulhu
Random.seed!(123)
# Definition of the model :
M₁ = Exponential(1.0)
M₂ = Exponential(1.0)
ρ = 0.5
Σ = [1.0 ρ; ρ 1.0]
C = GaussianCopula(Σ)
D = SklarDist(C, (M₁, M₂))
draws = rand(D, 1_000)
# This function works correctly, but is not ForwardDiff-able with respect to all the parameters of the model !
function getllh(ρ,a,b,draws)
D = SklarDist(GaussianCopula([1.0 ρ; ρ 1.0]),(Exponential(a),Exponential(b)))
return loglikelihood(D,draws)
end
getllh(0.5,1,1,draws) # OK
getllh(0.9,1,1,draws) # OK
getllh(0.5,3,2,draws) # OK
getllh(0.5,4,7,draws) # OK, Looks coherent.
ForwardDiff.derivative(ρ -> getllh(ρ,1,1,draws),0.1) # rho is too small, should be positive
ForwardDiff.derivative(ρ -> getllh(ρ,1,1,draws),0.9) # rho is too big, should be negative.
ForwardDiff.derivative(a -> getllh(0.5,1,a,draws),1) # Errors.
Which gives the following stacktrace :
julia> ForwardDiff.derivative(a -> getllh(0.5,1,a,draws),1) # Errors.
ERROR: TypeError: in typeassert, expected Float64, got a value of type ForwardDiff.Dual{Nothing, Float64, 1}
Stacktrace:
[1] setindex!(A::Vector{Float64}, x::ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Float64, 1}, i1::Int64)
@ Base .\array.jl:903
[2] _unsafe_copyto!(dest::Vector{Float64}, doffs::Int64, src::Vector{Real}, soffs::Int64, n::Int64)
@ Base .\array.jl:253
[3] unsafe_copyto!
@ .\array.jl:307 [inlined]
[4] _copyto_impl!
@ .\array.jl:331 [inlined]
[5] copyto!
@ .\array.jl:317 [inlined]
[6] copyto!
@ .\array.jl:343 [inlined]
[7] \(A::LinearAlgebra.LowerTriangular{Float64, LinearAlgebra.Adjoint{Float64, Matrix{Float64}}},
B::Vector{Real})
@ LinearAlgebra C:\Users\lrnv\AppData\Local\Programs\Julia-1.7.2\share\julia\stdlib\v1.7\LinearAlgebra\src\triangular.jl:1660
[8] invquad
@ C:\Users\lrnv\.julia\packages\PDMats\YXkIE\src\generics.jl:104 [inlined]
[9] sqmahal(d::ZeroMeanFullNormal{Tuple{Base.OneTo{Int64}}}, x::Vector{Real})
@ Distributions C:\Users\lrnv\.julia\packages\Distributions\O5xl5\src\multivariate\mvnormal.jl:267
[10] _logpdf
@ C:\Users\lrnv\.julia\packages\Distributions\O5xl5\src\multivariate\mvnormal.jl:143 [inlined]
[11] logpdf(d::ZeroMeanFullNormal{Tuple{Base.OneTo{Int64}}}, x::Vector{Real})
@ Distributions C:\Users\lrnv\.julia\packages\Distributions\O5xl5\src\common.jl:226
[12] _logpdf(C::GaussianCopula{2, Matrix{Float64}}, u::Vector{Real})
@ Copulas C:\Users\lrnv\.julia\dev\Copulas\src\EllipticalCopula.jl:15
[13] logpdf(d::GaussianCopula{2, Matrix{Float64}}, x::Vector{Real})
@ Distributions C:\Users\lrnv\.julia\packages\Distributions\O5xl5\src\common.jl:226
[14] _logpdf(S::SklarDist{GaussianCopula{2, Matrix{Float64}}, Tuple{Exponential{Float64}, Exponential{ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}}}}, u::SubArray{Float64, 1, Matrix{Float64}, Tuple{Base.Slice{Base.OneTo{Int64}}, Int64}, true})
@ Copulas C:\Users\lrnv\.julia\dev\Copulas\src\SklarDist.jl:27
[15] logpdf(d::SklarDist{GaussianCopula{2, Matrix{Float64}}, Tuple{Exponential{Float64}, Exponential{ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}}}}, x::SubArray{Float64, 1, Matrix{Float64}, Tuple{Base.Slice{Base.OneTo{Int64}}, Int64}, true})
@ Distributions C:\Users\lrnv\.julia\packages\Distributions\O5xl5\src\common.jl:226
[16] (::Base.Fix1{typeof(logpdf), SklarDist{GaussianCopula{2, Matrix{Float64}}, Tuple{Exponential{Float64}, Exponential{ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}}}}})(y::SubArray{Float64, 1, Matrix{Float64}, Tuple{Base.Slice{Base.OneTo{Int64}}, Int64}, true})
@ Base .\operators.jl:1136
[17] (::Base.MappingRF{Base.Fix1{typeof(logpdf), SklarDist{GaussianCopula{2, Matrix{Float64}}, Tuple{Exponential{Float64}, Exponential{ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}}}}}, Base.BottomRF{typeof(Base.add_sum)}})(acc::Base._InitialValue, x::SubArray{Float64, 1, Matrix{Float64}, Tuple{Base.Slice{Base.OneTo{Int64}}, Int64}, true})
@ Base .\reduce.jl:95
[18] _foldl_impl(op::Base.MappingRF{Base.Fix1{typeof(logpdf), SklarDist{GaussianCopula{2, Matrix{Float64}}, Tuple{Exponential{Float64}, Exponential{ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}}}}}, Base.BottomRF{typeof(Base.add_sum)}}, init::Base._InitialValue, itr::Distributions.EachVariate{1, Matrix{Float64}, Tuple{Base.OneTo{Int64}}, SubArray{Float64, 1, Matrix{Float64}, Tuple{Base.Slice{Base.OneTo{Int64}}, Int64}, true}, 1})
@ Base .\reduce.jl:58
[19] foldl_impl(op::Base.MappingRF{Base.Fix1{typeof(logpdf), SklarDist{GaussianCopula{2, Matrix{Float64}}, Tuple{Exponential{Float64}, Exponential{ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}}}}}, Base.BottomRF{typeof(Base.add_sum)}}, nt::Base._InitialValue, itr::Distributions.EachVariate{1, Matrix{Float64}, Tuple{Base.OneTo{Int64}}, SubArray{Float64, 1, Matrix{Float64}, Tuple{Base.Slice{Base.OneTo{Int64}}, Int64}, true}, 1})
@ Base .\reduce.jl:48
[20] mapfoldl_impl
@ .\reduce.jl:44 [inlined]
[21] #mapfoldl#244
@ .\reduce.jl:162 [inlined]
[22] mapfoldl
@ .\reduce.jl:162 [inlined]
[23] _mapreduce
@ .\reduce.jl:423 [inlined]
[24] _mapreduce_dim
@ .\reducedim.jl:330 [inlined]
[25] #mapreduce#725
@ .\reducedim.jl:322 [inlined]
[26] mapreduce
@ .\reducedim.jl:322 [inlined]
[27] #_sum#735
@ .\reducedim.jl:894 [inlined]
[28] _sum
@ .\reducedim.jl:894 [inlined]
[29] #sum#733
@ .\reducedim.jl:890 [inlined]
[30] sum
@ .\reducedim.jl:890 [inlined]
[31] loglikelihood(d::SklarDist{GaussianCopula{2, Matrix{Float64}}, Tuple{Exponential{Float64}, Exponential{ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}}}}, x::Matrix{Float64})
@ Distributions C:\Users\lrnv\.julia\packages\Distributions\O5xl5\src\common.jl:440
[32] getllh(ρ::Float64, a::Int64, b::ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1}, draws::Matrix{Float64})
@ Main c:\Users\lrnv\Desktop\julia testing\test2.jl:16
[33] (::var"#9#10")(a::ForwardDiff.Dual{ForwardDiff.Tag{var"#9#10", Int64}, Int64, 1})
@ Main c:\Users\lrnv\Desktop\julia testing\test2.jl:26
[34] derivative(f::var"#9#10", x::Int64)
@ ForwardDiff C:\Users\lrnv\.julia\packages\ForwardDiff\wAaVJ\src\derivative.jl:14
[35] top-level scope
@ c:\Users\lrnv\Desktop\julia testing\test2.jl:26
julia>
I tried Cthulhu’s @descend
to try understanding where in my code the mistake stays, but i could not understand where it is.
Could someone help me debug this ? I suspect this is my fault and therefore could be inside Copulas.jl
’s code, but I cannot find the mistake.
Thanks