継承とかその辺

今更書き古されてると思うんだけど、メモる。

  • __index

リストがインデクスや、メンバ名で"参照"されたときに(関数呼び出しを含む)代わりに参照される変数、リスト

  • __newindex

リストのインデクスや、メンバ名に"新規代入"されたときに代わりに参照される変数、リスト


baseのクラスがあって派生した時に参照カウンタみたいなstaticな変数が必要なときは__newindexを使わないと生成したオブジェクト先でその変数に代入した瞬間別の変数が生成されてしまう。


ダメな例

base = { name = "base", render = function(self) print( "name = " .. self.name) end, }
function base.new()
  local t = {
     a = 0,
  }
  return setmetatable( t, { __index = base, } )
end

a = base.new()
b = base.new()
c = base.new()

a.name = "a"  -- 代入した瞬間に別の変数としてa.nameが作成される。
b.name = "b" -- 代入した瞬間に別の変数としてb.nameが作成される。

a.render()
b.render()
c.render() -- 代入してないのでbaseのnameが使用される。
name = a
name = b
name = base


上記のような使い方をする分には十分正しいのか。でもstaticな感じには使えないね。
ということで

正しい方

base = { name = "base", render = function(self) print( "name = " .. self.name) end, }
function base.new()
  local t = {
     a = 0,
  }

  -- __newindexされたときもbaseを使用するようにする。
  return setmetatable( t, { __index = base, __newindex = base, } )
end

a = base.new()
b = base.new()
c = base.new()

a.name = "a"  
b.name = "b"

a.render()
b.render()
c.render() 
name = b
name = b
name = b


はい、これでオッケー。
この辺てsquirrelでは改善されてそう。
でももうちょっと枯れないと使えないよね。あと名前がダメね。発音しにくい。
スコリル?スクワール?シコレル?スクイレル?
なに?馬鹿にしてるの?このリス野郎が!!!


うそ。早く枯れてね。
言語名が「リス」なだけに拡張子はnut(木の実)なんだって。
おしゃれですね。