命名函数与...之间的差异匿名函数(Lua)

时间:2013-04-07 13:32:43

标签: functional-programming lua

这些myFunc之间有什么区别?

代码1

function wrapper()
    local someVariable = 0;
    function myFunc(n)
        if n > 0 then return myFunc(n-1) end
    end
    return myFunc;
end

代码2

function wrapper()
    local someVariable = 0;
    local myFunc = function(n)
        if n > 0 then return myFunc(n-1) end
    end
    return myFunc;
end

代码3

function wrapper()
    local someVariable = 0;
    local myFunc;
    myFunc = function(n)
        if n > 0 then return myFunc(n-1) end
    end;
    return myFunc;
end

因为当我在myFunc本身内部引用函数名myFunc时。他们的行为不一样。 (例如,upvalue someVariable ......有问题:-S)

2 个答案:

答案 0 :(得分:5)

[编辑:我误读了您的代码#2。]

代码#1将myFunc的全局值设置为该函数。因此,每次拨打wrapper时,您都会将此全局设置为新值。此外,对myFunc调用的任何引用都将指向此全局(可修改),而不是本地(这将是关闭的高价值)。

代码#2设置局部变量myFunc 然而 ,由于Lua的规则,在定义它的语句完成后,该局部变量才会进入范围。这允许你做这样的事情:

local x = x or 5

表达式中的x是先前声明的本地或全局。在评估x表达式之后,新的x or 5才会进入范围。

您的功能定义也是如此。因此,对myFunc的任何引用都将是全局变量,而不是本地。

代码#3创建一个局部变量myFunc。然后它将该变量设置为一个函数。因为在局部变量进入范围之后创建了函数,所以函数中对myFunc的引用将引用局部变量,而不是全局变量。

请注意,local function X相当于local X; X = function... local X = function...

答案 1 :(得分:2)

尼科尔的回答大多是正确的,但有一点值得指出:

在代码2中MyFunc不需要是一个全局变量,它可以是某个外部作用域中的局部变量,它将成为您正在创建的此函数的upvalue(相同的注释也适用于代码1)。例如,这将打印100

local function myFunc(n) return 100 end
function wrapper()
    local someVariable = 0;
    local myFunc = function(n)
        if n > 0 then return myFunc(n-1) end
    end
    return myFunc;
end
print(wrapper()(1))

总而言之,有四种方法可用于定义myFunc:

  1. local myFunc; myFunc = function(n) ... return myFunc(n-1) end
  2. local function myFunc(n) ... return myFunc(n-1) end
  3. local myFunc = function(n) ... return myFunc(n-1) end
  4. myFunc = function(n) ... return myFunc(n-1) end
  5. 1和2是完全等价物。 3将不会执行您期望的操作,因为它将使用执行local myFunc时可用的myFunc的任何定义(这可能指向MyFunc或全局变量的up值)。 4将起作用,但只是因为它会将新创建的函数分配给(再次)upvalue或全局变量(并在函数体中引用相同的值)。