I have multiple functions with the same pattern:
foo(rng::AbstractRNG, x::ValueType) = ...
which are commonly applied to arrays as
foo.(rng::AbstractRNG, a::Array{ValueType})
which is supposed to be equivalent to, essentially
reshape([foo(rng, x) for x in a], size(a))
rng here is a MersenneTwister-type value, but I guess the question applies to any other kind of RNG. For just the code above, I get an error
MethodError: no method matching length(::MersenneTwister)
In order to make it work I have to wrap a MersenneTwister in my own type and define length() and iterate() for it.
Is there some caveat Iām missing which is the reason these methods are not defined in Random?
In fact, since I need this kind of ābroadcastabilityā for many other types, I have the following abstract type defined:
abstract type BroadcastableSingleton end
Base.length(::BroadcastableSingleton) = 1
Base.iterate(x::BroadcastableSingleton) = (x, nothing)
Base.iterate(x::BroadcastableSingleton, state) = nothing
This reduces boilerplate code, but wonāt be too clear if there are already some complicated abstract type hierarchies in place. I wonder if there is a better way to do it? (Canāt help but miss Haskellās data classes here)