1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
|
vim.deepcopy = (function()
local function _id(v)
return v
end
local deepcopy_funcs = {
table = function(orig)
local copy = {}
if vim._empty_dict_mt ~= nil and getmetatable(orig) == vim._empty_dict_mt then
copy = vim.empty_dict()
end
for k, v in pairs(orig) do
copy[vim.deepcopy(k)] = vim.deepcopy(v)
end
if getmetatable(orig) then
setmetatable(copy, getmetatable(orig))
end
return copy
end,
['function'] = _id or function(orig)
local ok, dumped = pcall(string.dump, orig)
if not ok then
error(debug.traceback(dumped))
end
local cloned = loadstring(dumped)
local i = 1
while true do
local name = debug.getupvalue(orig, i)
if not name then
break
end
debug.upvaluejoin(cloned, i, orig, i)
i = i + 1
end
return cloned
end,
number = _id,
string = _id,
['nil'] = _id,
boolean = _id,
}
return function(orig)
local f = deepcopy_funcs[type(orig)]
if f then
return f(orig)
else
error("Cannot deepcopy object of type "..type(orig))
end
end
end)()
|