Skip to content

TypelessZero convert ambiguity with ForwardDiff dual numbers #153

Description

@THargreaves

TypelessZero has an ambiguous convert method when ForwardDiff dual numbers are involved. This occurs when trying to AD through a full particle filter pass (e.g. what happens when you initialise MH with an adtype since Turing v0.43.3.

MethodError: convert(::Type{ForwardDiff.Dual{T, V, N}}, ::GeneralisedFilters.TypelessZero) is ambiguous.

Candidates:
  convert(::Type{ForwardDiff.Dual{T, V, N}}, x::Number) where {T, V, N}
    @ ForwardDiff
  convert(::Type{T}, ::GeneralisedFilters.TypelessZero) where T<:Number
    @ GeneralisedFilters .../containers.jl:17

Context

This surfaces when using GeneralisedFilters inside a Turing model and running PMMH via Turing.externalsampler. As of Turing v0.43.3, parameter initialisation was unified between HMC and external samplers — external samplers now call logdensity_and_gradient during initialisation by default. This causes ForwardDiff dual numbers to flow through the filter even for gradient-free samplers, hitting the ambiguity.

Workaround

Ideally we would just do,

Turing.externalsampler(RobustAdaptiveMetropolis(; S=S); adtype=nothing)

but ExternalSampler forces a ADTypes.AbstractADType rather than an optional Nothing. This might be something that needs fixing upstream.

For now I'm just going to use Mooncake.

Fix

I think we can add a more specific convert method in containers.jl to resolve the ambiguity.

Base.convert(
    ::Type{ForwardDiff.Dual{T,V,N}}, ::TypelessZero
) where {T,V,N} = zero(ForwardDiff.Dual{T,V,N})

Though I question if this suggests there is a more fundamental structural issue so didn't want to jump in too quickly.

@charlesknipp would appreciate your thoughts.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions