将表重复传递给函数会分配更多内存吗?

时间:2012-09-21 22:48:02

标签: unit-testing garbage-collection lua pass-by-reference

我在Lua中有一个在表上操作的函数,重复向表中添加条目:

function DoStuff()
    local table = {};

    for i = 1, 1000 do
        local name, value = GetSomething(i);

        if (CheckSomething(name, value))
           table[name] = value
        end;
    end;
end;
我知道这很快; Lua有一个很好的哈希表算法。但现在我需要拆分我的部分功能,所以我可以对它进行单元测试:

function DoStuff()
    local table = {};

    for i = 1, 1000 do
        local name, value = GetSomething(i);

        --split out checking so it's testable
        table = ParseTheThing(table, name, value); 
    end;
end;

我知道Lua does not support passing paramters by reference,如果我需要在我的 table 中添加一个项目,Lua会复制一份,我必须返回该副本:

--Core checking function
function ParseTheThing(table, name, value)
   if (CheckSomething(name, value))
      table[name] = value
   end;

   return table;
end;

所以在我看来每次调用 CheckSomething 时,Lua都会创建另一个表,需要进行垃圾回收。

或许不是。也许Lua 支持支持通过引用传递参数,我可以简单地调用:

ParseTheThing(table, name, value); 

--Core checking function
function ParseTheThing(table, name, value)
   if (CheckSomething(name, value))
      table[name] = value
   end;
end;

如果我像我一样重构代码,Lua的垃圾收集器是否会被迫做更多工作?


备注

  • 不要将问题中使用的简化示例与我要问的问题混淆。
  • 我没有办法测量内存使用量或集合数量,所以我不能尝试

1 个答案:

答案 0 :(得分:5)

  

我知道Lua不支持通过引用传递参数

术语“引用”过载,引起很多混淆(特别是在Java world,我看到人们拒绝承认其中一个含义甚至存在)。

通过引用传递可能意味着:

  1. 将对象的位置传递给内存,而不是对象本身。这就是"pass by reference" in C的含义。从这个意义上讲,Java 通过引用传递,Lua也为其中的许多类型(用户数据,表格等)传递。

  2. 变量的别名,以便对别名的任何修改都会反映在原始文件中。这不仅仅是不通过价值;如果变量保存对象的位置,则可以通过别名指定其他位置。您不能为#1传递对对象的引用,而不是变量。 C#,C ++等支持这些类型的引用,但不支持C或Lua。

  3. 更简单:

    1. 按值传递:调用函数中的对象是被调用函数接收的对象的副本。
    2. 通过引用传递^ 1:调用函数中的对象可以被调用函数修改。
    3. 通过引用传递^ 2:调用函数中的变量可以被调用函数修改。
    4.   

      相反,如果我需要将一个项目添加到我的表

      只需传递表格 - 传递参考,而不是副本。