I want to create NamedTuple
s from a parametric type where the parameter is the desired type. Fields are computed using fieldtypes (in the MWE below, makezero
). From reading code in Base
, I came up with the following solution, is this the right way?
# make a field -- note that this is just for the MWE
makezero(::Type{T}) where T = zero(T)
"Make a `T` of zeros."
struct ZeroMaker{T <: Union{Tuple, NamedTuple}} end
_makezeros(::Type{Tuple{}}) = ()
_makezeros(::Type{T}) where T <: Tuple =
(makezero(Base.tuple_type_head(T)), _makezeros(Base.tuple_type_tail(T))...)
# this is a pattern I was familiar with
makezeros(::ZeroMaker{T}) where T <: Tuple = _makezeros(T)
# I am asking the question about this part
makezeros(::ZeroMaker{NamedTuple{N,S}}) where {N, S} =
NamedTuple{N}(_makezeros(S))
This works fine, is there anything I could do simpler/differently?
julia> T = Tuple{Int, Float64}
Tuple{Int64,Float64}
julia> NT = NamedTuple{(:a, :b), T}
NamedTuple{(:a, :b),Tuple{Int64,Float64}}
julia> @code_typed makezeros(ZeroMaker{T}())
CodeInfo(
1 1 ─ return (0, 0.0) │
) => Tuple{Int64,Float64}
julia> @code_typed makezeros(ZeroMaker{NT}())
CodeInfo(
1 1 ─ return $(QuoteNode((a = 0, b = 0.0))) │
) => NamedTuple{(:a, :b),Tuple{Int64,Float64}}