我想有一个接受DictNamedTuple作为输入的接口,但始终将输入转换为NamedTuple

给定Dict

julia> dd = Dict(:a => 1, :b => 2)
Dict{Symbol,Int64} with 2 entries:
  :a => 1
  :b => 2

我可以将其隐藏为NamedTuple
julia> (; dd...)
(a = 1, b = 2)

但是,这两者都分配了惊人的(对我来说)数量
julia> using BenchmarkTools

julia> @btime (; $dd...);
  1.033 μs (12 allocations: 896 bytes)

而且它不适用于嵌套的Dict,我想将其转换为嵌套的NamedTuple
julia> dd_nested = Dict(:a => 1, :b => Dict(:x => 3, :y => 4))
Dict{Symbol,Any} with 2 entries:
  :a => 1
  :b => Dict(:y=>4,:x=>3)

julia> (; dd_nested...)
(a = 1, b = Dict(:y => 4,:x => 3))

所需的输出等于
julia> (a = 1, b = (x = 3, y = 4))
(a = 1, b = (x = 3, y = 4))

最佳答案

关于什么:

unzip(d::Dict) = (;(p.first => unzip(p.second) for p in d)...)
unzip(d) = d

样品测试:
julia> unzip(dd)
(a = 1, b = (y = 4, x = 3))

关于内存分配,NamedTupleTools.jl似乎具有较小的内存占用量。但是,无论哪种情况,您都在这里创建了很多数据结构,因此很可能您将无法以任何更便宜的价格进行操作。

关于julia - 在Julia中将Dict有效地转换为NamedTuple,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/59755198/

10-13 02:33