简单的元组 |
|
nil或NaN
-- An interned 2-tuple type, in pure Lua. -- do -- The constructor makes a tuple function, which has its own -- intern table. local setmetatable = setmetatable local function tmaker(a) return {__index = function(t, b) local function tuple() return a, b end t[b] = tuple return tuple end, __mode = "kv" } end local meta = { __index = function(t, a) local v = setmetatable({}, tmaker(a)) t[a] = v return v end, __mode = "k" } return function() local intern = setmetatable({}, meta) return function(a, b) return intern[a][b] end end end
__mode行是可选的;实际上,我将此与非长期的元组缓存一起使用,并且更容易丢弃整个缓存。
用法:将以上内容放入一个名为TupleCache.lua的文件中。创建一个元组函数
local FooTuple = require"TupleCache"()
然后您可以使用元组函数创建新的FooTuples
local t = FooTuple(obja, objb)
FooTuple函数本身是缓存表的唯一引用,因此一旦FooTuple不再有引用,缓存表将被垃圾回收。但是,元组本身将继续存在;您只是无法创建新的元组。
要提取元组的值,请调用它
local obja, objb = t()
如果您确实需要能够包含nil和NaN的元组,则可以使用此版本
do -- The constructor makes a tuple function, which has its own -- intern table. local rawget, setmetatable = rawget, setmetatable local NIL, NAN = {}, {} local function check(t, a) if a == a and a ~= nil then return a end local fixa = a and NAN or NIL return fixa, rawget(t, fixa) end local function tmaker(a) return {__index = function(t, b) local fixb, tuple = check(t, b) tuple = tuple or function() return a, b end t[fixb] = tuple return tuple end } end local meta = { __index = function(t, a) local fixa, v = check(t, a) v = v or setmetatable({}, tmaker(a)) t[fixa] = v return v end } return function() local intern = setmetatable({}, meta) return function(a, b) return intern[a][b] end end end