ForwardDiff.jl
ForwardDiff.jl copied to clipboard
no promotion exists for ForwardDiff.Dual{N,T<:Real} and Float64
Hi all !
I would like to concatenate a vector of Dual with a Real as the following
T = 1
p = Array{Dual}(N)
k = 2
ps = vcat(p[1:k], T)
# z = rand(Categorical(ps))
Yet I get the error no promotion exists for ForwardDiff.Dual{N,T<:Real} and Float64.
Therefore I tried to extends the vcat function:
function Base.vcat{T<:Real}(a::Array{Dual{T}}, x::T)
N = length(a)
new_a = Array{Dual}(N+1)
new_a[1:N] = a
new_a[N+1] = Dual(x)
new_a
end
Unfortunatly this does not work. How shall I proceed ?
Thanks for your help, Emile
@xukai92 I remember we managed to solve this problem in Turing sometime ago. Could you help Emile out?
Yes, this promotion rule isn't defined because there's not really a correct/optimal behavior for this situation, given such a vague type signature. I guess the closest thing to a correct definition would probably be promote_rule(::Type{Dual}, ::Type{V}) where {V<:Real} = Dual{Void,V,0}, but throwing the error is a better idea than defining that promote rule.
What's your use case? Using Dual as an array's element type is almost certainly not what you want - it's too ill-specified to make sense for most use cases that I can think of.
@yebai We avoided this problem by constructing a new vector of dual from the real parts, which only happens when we need to use the vector in AD:
vi[range[i]] = ForwardDiff.Dual{CHUNKSIZE, Float64}(realpart(vals[i]), SEEDS[dim_count])
@emilemathieu I agree with @jrevels that the correct way of handling it depends on what how the new vector is used. Do you still need the gradient information from the previous vector?