检查 Lua 中的字符串是不是为 nil 或为空
Posted
技术标签:
【中文标题】检查 Lua 中的字符串是不是为 nil 或为空【英文标题】:Check if a string isn't nil or empty in Lua检查 Lua 中的字符串是否为 nil 或为空 【发布时间】:2013-11-08 23:43:24 【问题描述】:我目前有一些使用以下语法的 Lua 代码:
if (foo == nil or foo == '') then
foo = "some default value"
end
if 条件的目标是测试 foo 既不是空字符串,也不是 nil 值。
如果测试不是两个,这个代码可以简化为一个吗?
【问题讨论】:
那么,你到底在测试 foo、bar 还是 foo.bar?如果你有foo.bar
,你可以有一些像local function test(foo, bar) if (foo.bar == nil or foo.bar == '') then foo.bar = "some default value" end end
这样的函数来解决问题。
foo = foo 或“一些默认值”
假设您不希望 foo 的 'false' 计数,您可以使用 if (not foo) or (foo == '') then ...
,否则它会尽可能短。
@doog 坚持,不会工作。在 Lua 中 - '' == true
, nil == false
.
foo = (foo or '')=='' and 'default value' or foo
【参考方案1】:
您可以做的一件简单的事情是在函数中抽象测试。
local function isempty(s)
return s == nil or s == ''
end
if isempty(foo) then
foo = "default value"
end
【讨论】:
如果 s 的长度大于 0,你如何计算?例如:foo 长度为 2 你可以使用string.len
函数。但是要检查它是否大于零,s ~= ''
也可以。
thnx... 虽然问题是关于检查它是否 not 为空:p【参考方案2】:
如果测试不是两个,这个代码可以简化为一个吗?
nil
和 ''
是不同的值。如果您需要测试 s
两者都不是,IMO 您应该与两者进行比较,因为它使您的意图最清楚。
这和一些替代方案,以及它们生成的字节码:
if not foo or foo == '' then end
GETGLOBAL 0 -1 ; foo
TEST 0 0 0
JMP 3 ; to 7
GETGLOBAL 0 -1 ; foo
EQ 0 0 -2 ; - ""
JMP 0 ; to 7
if foo == nil or foo == '' then end
GETGLOBAL 0 -1 ; foo
EQ 1 0 -2 ; - nil
JMP 3 ; to 7
GETGLOBAL 0 -1 ; foo
EQ 0 0 -3 ; - ""
JMP 0 ; to 7
if (foo or '') == '' then end
GETGLOBAL 0 -1 ; foo
TEST 0 0 1
JMP 1 ; to 5
LOADK 0 -2 ; ""
EQ 0 0 -2 ; - ""
JMP 0 ; to 7
第二个在 Lua 5.1 和 5.2 中是最快的(无论如何在我的机器上),但差别很小。为了清楚起见,我会选择第一个。
【讨论】:
当foo
是false
时,第一个和第三个不做与第二个相同的事情。
使用#foo == 0
代替foo == ''
来检查空字符串怎么样?它有可能更快吗?
这不是一个坏主意。 Lua 字符串在内部保持其长度,因此您不必计算字符数。但是 Lua 也实习字符串,所以检查相等性也不需要查看字符;您只需检查对象是否相同。所以两个 应该 都很快,但结果是检索字符串长度的代码路径略长于从 VM 堆栈中获取两个对象指针以比较它们的代码路径,所以#foo == 0
在 5.1 中比 foo == ''
慢一点,在 5.2 和 5.3 中慢很多(由我机器上的基准测试确定)。
@NasBanov,# 运算符还有一些其他问题。这一次也是为表定义的,例如#==0
、#[2]='foo'==0
、#a='b'==0
。然后#42
会引发错误;一种可能不需要的行为...关于速度,# 运算符可以被覆盖(在 lua 5.2+ 中),实现也很慢,例如:#setmetatable(, __len=function()require'socket'.sleep(3)return 7 end)
;最后你可能会感到惊讶,但是对于表的默认 # 实现没有保证顺序(在某些情况下甚至可能是 O(n))。
@fcr - 谢谢,这是值得深思的 - 虽然我认为当我问我暗示知道手头的值是一个字符串时,即#str_foo
以上是关于检查 Lua 中的字符串是不是为 nil 或为空的主要内容,如果未能解决你的问题,请参考以下文章
spark中的isNullOrEmpty函数检查数据框中的列是不是为空或空字符串