Lua高次メタテーブル
4293 ワード
メタテーブル
Lua 5.1言語では、メタテーブル(metatable)の表現動作は、C++言語のオペレータリロードと同様であり、例えば、2つのLua配列の並列セットを計算するために「_add」メタメソッド(metamethod)をリロードすることができる.あるいは「_index」メソッドを再ロードして、独自のHash関数を定義します.Luaは、次のようにメタテーブルを処理するために非常に重要な2つの方法を提供します. setmetatable(table,metatable):このメソッドは、テーブルにメタテーブルを設定するために使用されます. getmetatable(table):このメソッドは、テーブルのメタテーブルオブジェクトを取得するために使用されます.
メタテーブルを設定する方法は簡単です.次のようにします.
上のコードは次のように簡単に書くことができます.
テーブルのオペレータ動作の変更
「_add」メタメソッドを変更して、コアの並列セットインスタンスを計算します.
加算を再ロードできるほか、Luaが提供するすべてのオペレータを再ロードできます.
メタメソッド
意味
"__add"
+アクション
"_sub"
-アクション「add」アクションと同様の動作
"__mul"
*アクション「add」アクションと同様の動作
"__div"
/アクション「add」アクションと同様の動作
"__mod"
%アクション「add」アクションと同様の動作
"__pow"
^(べき乗)アクションaddアクションと同様の動作
"__unm"
単元-アクション
"__concat"
..(文字列接続)アクション
"__len"
#アクション
"__eq"
==操作関数getcompandlerはluaがどのように1つのプロセッサを選択して比較操作を行うかを定義し、2つのオブジェクトタイプが同じで、対応する操作が同じメタメソッドがある場合にのみ有効です.
"__lt"
"__le"
<=操作
オペレータに加えて、次のメタメソッドをリロードすることもできます.次に、使用方法を順次説明します.
メタメソッド
意味
"__index"
table[key]にアクセスするには、ラベルを外す操作を使用します.
"__newindex"
指定した下付きタブに値を割り当てる[key]=value
"__tostring"
文字列に変換
"__call"
Luaが値を呼び出すと呼び出されます
"__mode"
弱表用(week table)
"__metatable"
metatableをアクセスから保護するために使用
__indexメタメソッド
次の例では、テーブルにキーが存在しない場合にメタテーブルでキーを検索する機能を実現します.
についてindexメタメソッドには、比較的高いテクニックがたくさんあります.例えば、_indexのメタメソッドは、関数でなくてもテーブルであってもよい.
まず{_index={}}をメタテーブルとするが_indexは関数ではなくテーブルを受け入れ、このテーブルには[2]=「world」というキー値ペアが含まれています.だからt[2]が自分の表に見つからないとき、_indexのテーブルを探して、[2]=「world」というキー値のペアを見つけました.+
__indexメタメソッドは、テーブル内の各値にデフォルト値を割り当てることもできます.および_newindexメタメソッドは,テーブルの読み取り,修正などの比較的高い機能を共同で監視し,読者自身が開発するのを待つ.
__tostringメタメソッド
JavaのtoString()関数と同様に、カスタム文字列変換を実現できます.
__callメタメソッド
__callメタメソッドの機能はC++の擬似関数に類似しており,通常のテーブルも呼び出すことができる.
__metatableメタメソッド
もし私たちがオブジェクトを保護したいなら、使用者が見えないようにmetatablesを変更することはできません.metatableを設定できます.metatableの値、getmetatableはこのドメインの値を返し、setmetatableを呼び出すとエラーが発生します.
記事の転載先:https://moonbingbing.gitbooks.io/openresty-best-practices/content/lua/metatable.html
Lua 5.1言語では、メタテーブル(metatable)の表現動作は、C++言語のオペレータリロードと同様であり、例えば、2つのLua配列の並列セットを計算するために「_add」メタメソッド(metamethod)をリロードすることができる.あるいは「_index」メソッドを再ロードして、独自のHash関数を定義します.Luaは、次のようにメタテーブルを処理するために非常に重要な2つの方法を提供します.
メタテーブルを設定する方法は簡単です.次のようにします.
local mytalbe = {}
local mymetatable = {}
setmetatable(mytable, mymetatable)
上のコードは次のように簡単に書くことができます.
local mytable = setmetatable({}, {})
テーブルのオペレータ動作の変更
「_add」メタメソッドを変更して、コアの並列セットインスタンスを計算します.
local set1 = {10, 20, 30} --
local set2 = {20, 40, 50} --
-- __add , self
local union = function (self, another)
local set = {}
local result = {}
--
for i, j in pairs(self) do set[j] = true end
for i, j in pairs(another) do set[j]= true end
--
for i, j in pairs(set) do table.insert(result, i) end
return result
end
setmetatable(set1, {__add = union}) -- set1 __add
local set3 = set1 + set2
for _, j in pairs(set3) do
io.write(j.." ") -- output: 30 50 20 40 10
end
加算を再ロードできるほか、Luaが提供するすべてのオペレータを再ロードできます.
メタメソッド
意味
"__add"
+アクション
"_sub"
-アクション「add」アクションと同様の動作
"__mul"
*アクション「add」アクションと同様の動作
"__div"
/アクション「add」アクションと同様の動作
"__mod"
%アクション「add」アクションと同様の動作
"__pow"
^(べき乗)アクションaddアクションと同様の動作
"__unm"
単元-アクション
"__concat"
..(文字列接続)アクション
"__len"
#アクション
"__eq"
==操作関数getcompandlerはluaがどのように1つのプロセッサを選択して比較操作を行うかを定義し、2つのオブジェクトタイプが同じで、対応する操作が同じメタメソッドがある場合にのみ有効です.
"__lt"
"__le"
<=操作
オペレータに加えて、次のメタメソッドをリロードすることもできます.次に、使用方法を順次説明します.
メタメソッド
意味
"__index"
table[key]にアクセスするには、ラベルを外す操作を使用します.
"__newindex"
指定した下付きタブに値を割り当てる[key]=value
"__tostring"
文字列に変換
"__call"
Luaが値を呼び出すと呼び出されます
"__mode"
弱表用(week table)
"__metatable"
metatableをアクセスから保護するために使用
__indexメタメソッド
次の例では、テーブルにキーが存在しない場合にメタテーブルでキーを検索する機能を実現します.
mytable = setmetatable({key1 = "value1"}, --
{__index = function(self, key) --
if key == "key2" then
return "metatablevalue"
end
end
})
print(mytable.key1, mytable.key2) -- output: value1 metatablevalue
についてindexメタメソッドには、比較的高いテクニックがたくさんあります.例えば、_indexのメタメソッドは、関数でなくてもテーブルであってもよい.
t = setmetatable({[1] = "hello"}, {__index = {[2] = "world"}})
print(t[1], t[2]) -- output: hello world
まず{_index={}}をメタテーブルとするが_indexは関数ではなくテーブルを受け入れ、このテーブルには[2]=「world」というキー値ペアが含まれています.だからt[2]が自分の表に見つからないとき、_indexのテーブルを探して、[2]=「world」というキー値のペアを見つけました.+
__indexメタメソッドは、テーブル内の各値にデフォルト値を割り当てることもできます.および_newindexメタメソッドは,テーブルの読み取り,修正などの比較的高い機能を共同で監視し,読者自身が開発するのを待つ.
__tostringメタメソッド
JavaのtoString()関数と同様に、カスタム文字列変換を実現できます.
arr = {1, 2, 3, 4}
arr = setmetatable(arr, {__tostring = function (self)
local result = '{'
local sep = ''
for _, i in pairs(self) do
result = result .. sep .. i
sep=', '
end
result = result .. '}'
return result
end})
print(arr) --> {1, 2, 3, 4}
__callメタメソッド
__callメタメソッドの機能はC++の擬似関数に類似しており,通常のテーブルも呼び出すことができる.
functor = {}
function func1(self, arg)
print ("called from", arg)
end
setmetatable(functor, {__call = func1})
functor("functor") --> called from functor
print(functor) --> output:0x00076fc8 ( )
__metatableメタメソッド
もし私たちがオブジェクトを保護したいなら、使用者が見えないようにmetatablesを変更することはできません.metatableを設定できます.metatableの値、getmetatableはこのドメインの値を返し、setmetatableを呼び出すとエラーが発生します.
Object = setmetatable({}, {__metatable = "You cannot access here"})
print(getmetatable(Object)) --> You cannot access here
setmetatable(Object, {}) -->
記事の転載先:https://moonbingbing.gitbooks.io/openresty-best-practices/content/lua/metatable.html