On a random walk through options, I seem to have hit upon
copynode(o)=XML.Node(o.nodetype, o.tag, o.attributes, o.value, isnothing(o.children) ? nothing : [copynode(x) for x in o.children])
Which recursively copies a node and all its children.
As far as I can tell, this gives the same result as deepcopy
but is quite a bit faster. Here, I’m just using an XML file representing an Excel worksheet (nested a few levels deep).
julia> using XML, BenchmarkTools, XLSX
julia> copynode(o)=XML.Node(o.nodetype, o.tag, o.attributes, o.value, isnothing(o.children) ? nothing : [copynode(x) for x in o.children])
copynode (generic function with 1 method)
julia> deepcopynode(o) = deepcopy(o)
deepcopynode (generic function with 1 method)
julia> function createCfx(rule, f)
cfx=f(rule)
cfvo = XML.Element("x14:cfvo", type="percent")
push!(cfvo, XML.Element("xm:f", XML.Text("dummy")))
push!(cfx[end], f(cfvo))
push!(cfx[end], f(cfvo))
push!(cfx[end], f(cfvo))
cfx[1]["iconSet"] = "4Arrows"
return cfx
end
createCfx (generic function with 1 method)
julia> f=XLSX.opentemplate(raw"C:\Users\tim\OneDrive\Documents\Julia\XLSX\iconKey.xlsx")
XLSXFile("C:\Users\tim\OneDrive\Documents\Julia\XLSX\iconKey.xlsx") containing 1 Worksheet
sheetname size range
-------------------------------------------------
Sheet1 4x13 A1:M4
julia> rule = XLSX.get_worksheet_xml_document(f[1])
Node Document (2 children)
julia> @benchmark cfx=createCfx($rule, $copynode)
BenchmarkTools.Trial: 10000 samples with 1 evaluation per sample.
Range (min … max): 86.100 μs … 7.979 ms ┊ GC (min … max): 0.00% … 97.99%
Time (median): 93.900 μs ┊ GC (median): 0.00%
Time (mean ± σ): 109.910 μs ± 153.160 μs ┊ GC (mean ± σ): 6.75% ± 5.06%
▁▇█▃
▁▂▄████▇▄▂▂▂▁▁▁▁▂▂▂▂▃▃▂▂▂▂▂▂▁▂▂▃▃▃▃▂▂▂▂▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁▁ ▂
86.1 μs Histogram: frequency by time 159 μs <
Memory estimate: 205.73 KiB, allocs estimate: 4520.
julia> rule2 = XLSX.get_worksheet_xml_document(f[1])
Node Document (2 children)
julia> cfx2=createCfx(rule2, deepcopynode)
Node Document (2 children)
julia> rule2 = XLSX.get_worksheet_xml_document(f[1])
Node Document (2 children)
julia> @benchmark cfx2=createCfx($rule2, $deepcopynode)
BenchmarkTools.Trial: 9872 samples with 1 evaluation per sample.
Range (min … max): 438.400 μs … 4.798 ms ┊ GC (min … max): 0.00% … 87.00%
Time (median): 456.900 μs ┊ GC (median): 0.00%
Time (mean ± σ): 505.863 μs ± 259.013 μs ┊ GC (mean ± σ): 4.52% ± 7.66%
▅▇█▇▆▆▅▄▂▁▁▁ ▁▂▂▂▂▁ ▁▁▁▁▁▁▁▂▁▁ ▂
▆██████████████▇▆▆▅▆▇▇▆▇██████████▇▆▇▇▇▇████████████▇▇▆▅▅▄▄▄▄ █
438 μs Histogram: log(frequency) by time 698 μs <
Memory estimate: 537.81 KiB, allocs estimate: 12190.
julia> cfx=createCfx(rule, copynode)
Node Document (2 children)
julia> rule = XLSX.get_worksheet_xml_document(f[1])
Node Document (2 children)
julia> cfx=createCfx(rule, copynode)
Node Document (2 children)
julia> rule2 = XLSX.get_worksheet_xml_document(f[1])
Node Document (2 children)
julia> cfx2=createCfx(rule2, copynode)
Node Document (2 children)
julia> cfx==cfx2
true