Advertisement
Guest User

table compare benchmark

a guest
Oct 31st, 2014
208
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 5.16 KB | None | 0 0
  1. function _TableCompare(table1, table2)
  2.     local n1, n2 = 0, 0
  3.     for k, v in pairs(table1) do
  4.         n1 = n1 + 1
  5.         local v2 = table2[k]
  6.         if not v2 then return false
  7.         elseif type(v) == 'table' then
  8.         if type(v2) ~= 'table' or not _TableCompare(v, v2) then return false end
  9.         elseif table2[k] ~= v then return false end
  10.     end
  11.     for k, v in pairs(table2) do
  12.         if n2 == n1 then return false end
  13.         n2 = n2 + 1
  14.     end
  15.     return n1 == n2
  16. end
  17.  
  18. function areTablesEqual1(table1, table2)
  19.     for k, v in pairs(table1) do
  20.         if table2[k] ~= v then
  21.             return false
  22.         end
  23.     end
  24.     for k, v in pairs(table2) do
  25.         if table1[k] ~= v then
  26.             return false
  27.         end
  28.     end
  29.     return true
  30. end
  31.  
  32. function deepcompare(t1,t2,ignore_mt)
  33.     local ty1 = type(t1)
  34.     local ty2 = type(t2)
  35.     if ty1 ~= ty2 then return false end
  36.     -- non-table types can be directly compared
  37.     if ty1 ~= 'table' and ty2 ~= 'table' then return t1 == t2 end
  38.     -- as well as tables which have the metamethod __eq
  39.     local mt = getmetatable(t1)
  40.     if not ignore_mt and mt and mt.__eq then return t1 == t2 end
  41.     for k1,v1 in pairs(t1) do
  42.         local v2 = t2[k1]
  43.         if v2 == nil or not deepcompare(v1,v2) then return false end
  44.     end
  45.     for k2,v2 in pairs(t2) do
  46.         local v1 = t1[k2]
  47.         if v1 == nil or not deepcompare(v1,v2) then return false end
  48.     end
  49.     return true
  50. end
  51.  
  52. function deepcompare2(t1,t2,ignore_mt)
  53.     -- t1 and t2 must be of 'table' types otherwise behaviour is undefined
  54.     local mt = getmetatable(t1)
  55.     if not ignore_mt and mt and mt.__eq then return t1 == t2 end
  56.     for k1,v1 in pairs(t1) do
  57.         local v2 = t2[k1]
  58.         if v2 == nil then return false end
  59.         if type(v1) == 'table' and type(v2) == 'table' then
  60.             if not deepcompare2(v1,v2) then return false end
  61.         elseif v1 ~= v2 then return false end
  62.     end
  63.     for k2,v2 in pairs(t2) do
  64.         local v1 = t1[k2]
  65.         if v1 == nil then return false end
  66.         -- no need to compare value at k2 again since it was already handled by the first loop
  67.     end
  68.     return true
  69. end
  70.  
  71. function nkTablesEqu(t1, t2)
  72.     local k1,v1;
  73.     for k, v in pairs(t1) do
  74.         k1,v1=next(t2,k1)
  75.         if v~=v1 or k~=k1 then return false end
  76.     end
  77.     k1,v1=next(t2,k1);
  78.     if v1~=nil then return false; end
  79.     return true
  80. end
  81.  
  82. -----------------------------------------------------
  83. function gen_table(n)
  84.     t={}
  85.     for i=1, n do
  86.         t[string.format("%08d", i)] = i
  87.     end
  88.     return t
  89. end
  90.  
  91. function gen_table1(n)
  92.     t={}
  93.     x=math.random(1, n)
  94.     for i=1, n do
  95.         if i == x then
  96.             t[string.format("%08d", i)] = math.random()
  97.         else
  98.             t[string.format("%08d", i)] = i
  99.         end
  100.     end
  101.     return t
  102. end
  103.  
  104. -----------------------------------------------------
  105.  
  106. function benchmark_compare_tables(cmp_func_, t1_, t2_, ttype, expected_result)
  107.     local cmp_func = cmp_func_
  108.     local t1 = t1_
  109.     local t2 = t2_
  110.     if cmp_func(t1, t2) ~= expected_result then
  111.         io.write(" FAILED to compare '", ttype, "' tables, benchmarking anyway...")
  112.     else
  113.         io.write(" benchmarking '", ttype, "' tables...")
  114.     end
  115.     local start = os.clock()
  116.     for i = 1, 100000 do
  117.         cmp_func(t1, t2)
  118.     end
  119.     local stop = os.clock()
  120.     io.write(" time: ", stop - start, "\n")
  121. end
  122.  
  123. function run_test(cmp_func)
  124.     local a1={1,2,3,4}
  125.     local a2={1,2,3,4}
  126.     benchmark_compare_tables(cmp_func, a1, a2, "array", true)
  127.  
  128.     local t1={["c"]=3,["a"]=1,["aa"]=6,["b"]=2,["d"]=4,["ba"]=7,["ca"]=8}
  129.     benchmark_compare_tables(cmp_func, t1, t1, "same", true)
  130.  
  131.     local t2={["ca"]=8,["b"]=2,["a"]=1,["aa"]=6,["c"]=3,["d"]=4,["ba"]=7}
  132.     benchmark_compare_tables(cmp_func, t1, t2, "shuffled", true)
  133.  
  134.     local t11={["c"]=3,["a"]=1,["aa"]=6,["b"]=2,["d"]=4,["ba"]=7,["ca"]=9}
  135.     benchmark_compare_tables(cmp_func, t1, t11, "same size, single different value", false)
  136.  
  137.     local nested1 = {k1="value1", nested={k2="value3"}}
  138.     local nested2 = {k1="value1", nested={k2="value3"}}
  139.     benchmark_compare_tables(cmp_func, nested1, nested2, "nested", true)
  140.  
  141.     local nested22 = {k1="value1", nested="value2"}
  142.     benchmark_compare_tables(cmp_func, nested1, nested2, "nested vs non-nested", true)
  143.  
  144.     local metatable = {__eq = function(t1, t2) return true end}
  145.     local m1={k1=1}
  146.     local m2={k1="one"}
  147.     setmetatable(m1, metatable)
  148.     setmetatable(m2, metatable)
  149.     benchmark_compare_tables(cmp_func, m1, m2, "with metatable.__eq", true)
  150.  
  151.     local t1000_1=gen_table(1000)
  152.     local t1000_2=gen_table(1000)
  153.     benchmark_compare_tables(cmp_func, t1000_1, t1000_2, "size=1000", true)
  154.     local t1000_3=gen_table1(1000)
  155.     benchmark_compare_tables(cmp_func, t1000_1, t1000_3, "size=1000 vs random", false)
  156. end
  157.  
  158. math.randomseed(os.time())
  159.  
  160. io.write("--- areTablesEqual1\n")
  161. run_test(areTablesEqual1)
  162. io.write("--- _TableCompare\n")
  163. run_test(_TableCompare)
  164. io.write("--- deepcompare\n")
  165. run_test(deepcompare)
  166. io.write("--- deepcompare2\n")
  167. run_test(deepcompare2)
  168. io.write("--- nkTablesEq\n")
  169. run_test(nkTablesEqu)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement