从C中的Lua函数返回'nil'与返回0值

Nic*_* M. 9 c lua

一些Lua函数返回nil以通知用户该函数不能执行某些任务(例如tonumber(),string.find()).

在C中,returnig nil就是这样完成的:

int some_function(lua_State* L) {
  ...
  if (some condition) {
      lua_pushnil(L);
      return 1;
  }
  ...
}
Run Code Online (Sandbox Code Playgroud)

但是,我想知道是否可以做以下事情:

int some_function(lua_State* L) {
  ...
  if (some condition) {
      return 0;
  }
  ...
}
Run Code Online (Sandbox Code Playgroud)

它更短.我尝试了它似乎有效,但我不知道这是否是按设计的.我检查了Lua的源代码,我没有看到这种return 0模式,所以我想知道这样做是否合法.

两种不同的返回方式是否nil相同?

(顺便说一句,我知道所有关于通过异常发出的信号错误(也就是说),lua_error()所以请不要提及它.)

更新:

我现在看到两种方法之间存在细微的差别:print((function() end)())没有打印,而是print((function() return nil end)())打印"nil".我不知道这有多重要.

Lor*_*ica 14

Lua中的函数可能会返回nil但也可能不返回任何内容,并且此行为并不完全等效,尽管在大多数情况下会产生相同的结果.

以下Lua脚本向您展示了如何检测函数返回的返回值的数量:

local function PrintNRetVals( ... )
    local nargs = select( '#', ... )
    print( "Number of values returned: " .. nargs )
end

local function ReturningSomething()
    return "hello"
end

local function ReturningNil()
    return nil
end

local function ReturningNothing()
    return
end


PrintNRetVals( ReturningSomething() )   --> 1
PrintNRetVals( ReturningNil() )         --> 1
PrintNRetVals( ReturningNothing() )     --> 0
Run Code Online (Sandbox Code Playgroud)

我说行为几乎是等价的,因为只要你尝试将一个函数的结果分配给变量,变量将nil在两种情况下得到,因此后续代码将无法区分.但是,正如我上面所示,如果你真的需要,你可以发现差异.


Mar*_*rio 5

是的,这是完全有效的.如果您尝试请求/分配的返回值多于(无论您是尝试获得一个还是十个),您将获得nil未定义的返回值(即未返回的那些).

function test1()
    return 5
end

local a, b = test1()
-- a = 5, b = nil

function test2()
    return 1, 2
end

local c, d, e = test2()
-- c = 1, d = 2, e = nil

function test3()
end

local f, g = test3()
-- f = nil, g = nil
Run Code Online (Sandbox Code Playgroud)

您可能无法在Lua的源代码中找到它,因为它不是特例或任何特殊情况.这只是Lua处理返回值的通用方法.

更新:

您在尝试打印返回值时注意到的差异是,这不仅仅是一项任务.当然,返回nil和返回之间几乎没有什么区别- 并且可以在那里区分.最后,您必须确保正确记录您的功能行为,即告诉用户应该发生什么.例如,返回nil(或获取nil赋值)可能表示错误状态,但也可能在出现错误时不返回任何内容,nil如果某些值应该无效或nil(但没有发生错误)则返回.