开发者

Lua: implicit table creation with string keys - why the extra brackets?

开发者 https://www.devze.com 2023-01-31 17:19 出处:网络
Say that you wa开发者_StackOverflow中文版nt to create a Lua table, and all its keys are valid lua identifiers. Then you can use the key=value syntax:

Say that you wa开发者_StackOverflow中文版nt to create a Lua table, and all its keys are valid lua identifiers. Then you can use the key=value syntax:

local niceTable = { I=1, like=1, this=1, syntax=1 }

If however your strings are not "identifiable", then you have to use the ['key']=value syntax:

local operators = { ['*']="Why", ['+']="the", ['/']="brackets", ['?']='?' }

I'm a bit baffled about this. What are those brackets doing there? What do they mean?


They identify the contained string as a key in the resulting table. The first form, you could consider as equal to

local niceTable = {}
niceTable.I = 1;
niceTable.like = 1;

The second form is equal to

local operators = {}
operators['*'] = "Why";
operators['+'] = "The";

The difference is purely syntactic sugar, except where the first one uses identifiers, so it has to follow the identifier rules, such as doesn't start with a number and interpret-time constant, and the second form uses any old string, so it can be determined at runtime, for example, and a string that's not a legal identifier. However, the result is fundamentally the same. The need for the brackets is easily explained.

local var = 5;
local table = {
    var = 5;
};
-- table.var = 5;

Here, var is the identifier, not the variable.

local table = {
    [var] = 5;
};
-- table[5] = 5;

Here, var is the variable, not the identifier.


The normal syntax for indexing a table is t[val]. For string keys only, Lua provides an alternate syntax, where t.foo is exactly equivalent to t["foo"]. This is purely a syntactical convenience, so-called 'syntax sugar'. It doesn't add functionality, it just gives you a less cluttered syntax for using strings as named fields.

There are a lot of strings keys this won't work for:

t["hello_world"] => t.hello_world  -- works
t["hello world"] => t.hello world  -- oops, space in the string
t["5 * 3"]       => t.5 * 3        -- oops
t['[10]']        => t.[10]         -- oops

Basically it only works if the string key would be a valid identifier.

Again, tables are indexed via [], and in most cases you need to use them:

t = {
   -- [key]           = value
   [10]               = "ten", -- number key, string value
   ["print function"] = print, -- string key, function value
   ["sub table"]      = {},    -- string key, table value
   [print]            = 111,   -- function key, number value
   ["foo"]            = 123,   -- string key, number value
}

Only if you're using a string key which would work as a valid identifier (no spaces, contains only word characters, numbers, or underlines, and doesn't begin with a number) can you use the shortcut syntax. For the table above, that would be only 'foo':

t = {
   -- [key]           = value
   [10]               = "ten", -- number key, string value
   ["print function"] = print, -- string key, function value
   ["sub table"]      = {},    -- string key, table value
   [print]            = 111,   -- function key, number value
   foo                = 123,   -- string key, number value
}
0

精彩评论

暂无评论...
验证码 换一张
取 消