@@ -7,7 +7,7 @@ using ForwardDiff: Dual, partials, GradientConfig, JacobianConfig, HessianConfig
77 gradient, hessian, jacobian, gradient!, hessian!, jacobian!,
88 extract_gradient!, extract_jacobian!, extract_value!,
99 vector_mode_gradient, vector_mode_gradient!,
10- vector_mode_jacobian, vector_mode_jacobian!, valtype, value, _lyap_div!
10+ vector_mode_jacobian, vector_mode_jacobian!, valtype, value
1111using DiffResults: DiffResult, ImmutableDiffResult, MutableDiffResult
1212
1313@generated function dualize (:: Type{T} , x:: StaticArray ) where T
2323
2424@inline static_dual_eval (:: Type{T} , f, x:: StaticArray ) where T = f (dualize (T, x))
2525
26+ # To fix method ambiguity issues:
2627function LinearAlgebra. eigvals (A:: Symmetric{<:Dual{Tg,T,N}, <:StaticArrays.StaticMatrix} ) where {Tg,T<: Real ,N}
27- λ,Q = eigen (Symmetric (value .(parent (A))))
28- parts = ntuple (j -> diag (Q' * getindex .(partials .(A), j) * Q), N)
29- Dual {Tg} .(λ, tuple .(parts... ))
28+ return ForwardDiff. _eigvals (A)
3029end
31-
3230function LinearAlgebra. eigen (A:: Symmetric{<:Dual{Tg,T,N}, <:StaticArrays.StaticMatrix} ) where {Tg,T<: Real ,N}
33- λ = eigvals (A)
34- _,Q = eigen (Symmetric (value .(parent (A))))
35- parts = ntuple (j -> Q* ForwardDiff. _lyap_div! (Q' * getindex .(partials .(A), j) * Q - Diagonal (getindex .(partials .(λ), j)), value .(λ)), N)
36- Eigen (λ,Dual {Tg} .(Q, tuple .(parts... )))
31+ return ForwardDiff. _eigen (A)
3732end
3833
34+ # For `MMatrix` we can use the in-place method
35+ ForwardDiff. _lyap_div!! (A:: StaticArrays.MMatrix , λ:: AbstractVector ) = ForwardDiff. _lyap_div! (A, λ)
36+
3937# Gradient
40- @inline ForwardDiff. gradient (f, x:: StaticArray ) = vector_mode_gradient (f, x)
41- @inline ForwardDiff. gradient (f, x:: StaticArray , cfg:: GradientConfig ) = gradient (f, x)
42- @inline ForwardDiff. gradient (f, x:: StaticArray , cfg:: GradientConfig , :: Val ) = gradient (f, x)
38+ @inline ForwardDiff. gradient (f:: F , x:: StaticArray ) where F = vector_mode_gradient (f, x)
39+ @inline ForwardDiff. gradient (f:: F , x:: StaticArray , cfg:: GradientConfig ) where F = gradient (f, x)
40+ @inline ForwardDiff. gradient (f:: F , x:: StaticArray , cfg:: GradientConfig , :: Val ) where F = gradient (f, x)
4341
44- @inline ForwardDiff. gradient! (result:: Union{AbstractArray,DiffResult} , f, x:: StaticArray ) = vector_mode_gradient! (result, f, x)
45- @inline ForwardDiff. gradient! (result:: Union{AbstractArray,DiffResult} , f, x:: StaticArray , cfg:: GradientConfig ) = gradient! (result, f, x)
46- @inline ForwardDiff. gradient! (result:: Union{AbstractArray,DiffResult} , f, x:: StaticArray , cfg:: GradientConfig , :: Val ) = gradient! (result, f, x)
42+ @inline ForwardDiff. gradient! (result:: Union{AbstractArray,DiffResult} , f:: F , x:: StaticArray ) where F = vector_mode_gradient! (result, f, x)
43+ @inline ForwardDiff. gradient! (result:: Union{AbstractArray,DiffResult} , f:: F , x:: StaticArray , cfg:: GradientConfig ) where F = gradient! (result, f, x)
44+ @inline ForwardDiff. gradient! (result:: Union{AbstractArray,DiffResult} , f:: F , x:: StaticArray , cfg:: GradientConfig , :: Val ) where F = gradient! (result, f, x)
4745
4846@generated function extract_gradient (:: Type{T} , y:: Real , x:: S ) where {T,S<: StaticArray }
4947 result = Expr (:tuple , [:(partials (T, y, $ i)) for i in 1 : length (x)]. .. )
6563end
6664
6765# Jacobian
68- @inline ForwardDiff. jacobian (f, x:: StaticArray ) = vector_mode_jacobian (f, x)
69- @inline ForwardDiff. jacobian (f, x:: StaticArray , cfg:: JacobianConfig ) = jacobian (f, x)
70- @inline ForwardDiff. jacobian (f, x:: StaticArray , cfg:: JacobianConfig , :: Val ) = jacobian (f, x)
66+ @inline ForwardDiff. jacobian (f:: F , x:: StaticArray ) where F = vector_mode_jacobian (f, x)
67+ @inline ForwardDiff. jacobian (f:: F , x:: StaticArray , cfg:: JacobianConfig ) where F = jacobian (f, x)
68+ @inline ForwardDiff. jacobian (f:: F , x:: StaticArray , cfg:: JacobianConfig , :: Val ) where F = jacobian (f, x)
7169
72- @inline ForwardDiff. jacobian! (result:: Union{AbstractArray,DiffResult} , f, x:: StaticArray ) = vector_mode_jacobian! (result, f, x)
73- @inline ForwardDiff. jacobian! (result:: Union{AbstractArray,DiffResult} , f, x:: StaticArray , cfg:: JacobianConfig ) = jacobian! (result, f, x)
74- @inline ForwardDiff. jacobian! (result:: Union{AbstractArray,DiffResult} , f, x:: StaticArray , cfg:: JacobianConfig , :: Val ) = jacobian! (result, f, x)
70+ @inline ForwardDiff. jacobian! (result:: Union{AbstractArray,DiffResult} , f:: F , x:: StaticArray ) where F = vector_mode_jacobian! (result, f, x)
71+ @inline ForwardDiff. jacobian! (result:: Union{AbstractArray,DiffResult} , f:: F , x:: StaticArray , cfg:: JacobianConfig ) where F = jacobian! (result, f, x)
72+ @inline ForwardDiff. jacobian! (result:: Union{AbstractArray,DiffResult} , f:: F , x:: StaticArray , cfg:: JacobianConfig , :: Val ) where F = jacobian! (result, f, x)
7573
7674@generated function extract_jacobian (:: Type{T} , ydual:: StaticArray , x:: S ) where {T,S<: StaticArray }
7775 M, N = length (ydual), length (x)
@@ -110,18 +108,18 @@ end
110108end
111109
112110# Hessian
113- ForwardDiff. hessian (f, x:: StaticArray ) = jacobian (y -> gradient (f, y), x)
114- ForwardDiff. hessian (f, x:: StaticArray , cfg:: HessianConfig ) = hessian (f, x)
115- ForwardDiff. hessian (f, x:: StaticArray , cfg:: HessianConfig , :: Val ) = hessian (f, x)
111+ ForwardDiff. hessian (f:: F , x:: StaticArray ) where F = jacobian (y -> gradient (f, y), x)
112+ ForwardDiff. hessian (f:: F , x:: StaticArray , cfg:: HessianConfig ) where F = hessian (f, x)
113+ ForwardDiff. hessian (f:: F , x:: StaticArray , cfg:: HessianConfig , :: Val ) where F = hessian (f, x)
116114
117- ForwardDiff. hessian! (result:: AbstractArray , f, x:: StaticArray ) = jacobian! (result, y -> gradient (f, y), x)
115+ ForwardDiff. hessian! (result:: AbstractArray , f:: F , x:: StaticArray ) where F = jacobian! (result, y -> gradient (f, y), x)
118116
119- ForwardDiff. hessian! (result:: MutableDiffResult , f, x:: StaticArray ) = hessian! (result, f, x, HessianConfig (f, result, x))
117+ ForwardDiff. hessian! (result:: MutableDiffResult , f:: F , x:: StaticArray ) where F = hessian! (result, f, x, HessianConfig (f, result, x))
120118
121- ForwardDiff. hessian! (result:: ImmutableDiffResult , f, x:: StaticArray , cfg:: HessianConfig ) = hessian! (result, f, x)
122- ForwardDiff. hessian! (result:: ImmutableDiffResult , f, x:: StaticArray , cfg:: HessianConfig , :: Val ) = hessian! (result, f, x)
119+ ForwardDiff. hessian! (result:: ImmutableDiffResult , f:: F , x:: StaticArray , cfg:: HessianConfig ) where F = hessian! (result, f, x)
120+ ForwardDiff. hessian! (result:: ImmutableDiffResult , f:: F , x:: StaticArray , cfg:: HessianConfig , :: Val ) where F = hessian! (result, f, x)
123121
124- function ForwardDiff. hessian! (result:: ImmutableDiffResult , f, x:: StaticArray )
122+ function ForwardDiff. hessian! (result:: ImmutableDiffResult , f:: F , x:: StaticArray ) where F
125123 T = typeof (Tag (f, eltype (x)))
126124 d1 = dualize (T, x)
127125 d2 = dualize (T, d1)
0 commit comments