lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


Op So. 17 Mrt. 2019 om 18:25 het temp 213 qwe <temp213@gorodok.net> geskryf:
>
> On Sun, 17 Mar 2019 12:42:32 -0300
>   Luiz Henrique de Figueiredo <lhf@tecgraf.puc-rio.br> wrote:
> > What problem does this proposal solve?
>
> Absence of default metatables.
>
> This results, in some cases, that all the tables needs to be
> created by some additional constructor function, that set the
> metatable, which is a bit annoying, instead of setting it
> once, for all the tables.
>
> Which actually is not a problem, but more like a syntactic
> sugar.
>
> Plus it makes it uniform with the strings & strings library.
> ("string"):reverse()
> ({1,5,2,4,3}):sort()

Since 'table' is Lua's only data structure, which does duty for
arrays, sets, dictionaries, lists, queues, stacks, XML encodings,
matrices etc, it would be quite annoying to find every table one
creates pre-equipped with a metatable that serves only one of these.

Here is my full and complete class system. It is written to be the
body of a file but I often simply insert the code sans comments and
final 'return' at the top of a program.

--[[    Minimal support for classes
  Returns the class definer "class", and creates a global function "is"
    unless the global variable "is" is already in use.

USAGE
  1. Define a new class:   MyClass = class("my class",index,newindex)
       'index(class,key)' and 'newindex(object,key,value)' are optional
       metamethods. 'index' can be used to inherit an existing class.
  2. Add methods to it:    MyClass.method = function(self,...)"
                    or:    function MyClass:method(...)
  3. Reserved method:      MyClass:init(...)  [optional]
  4. Create new object     obj = MyClass(...)"
       If MyClass.init has been defined, obj:init(...) will be called before
       returning the object.

HOW IT WORKS
  MyClass is the metatable, the method table and (via its __call metamethod)
the default constructor for the new class, all rolled into one.
--]]

local new = function(class,...)
  local object = setmetatable({},class)
  if object.init then object:init(...) end
  return object
end

local class = function(name,index,newindex)
  local mt = setmetatable({__name=name,__newindex=newindex},
    {__call=new,__index=index})
  mt.__index = mt
  return mt
end

local is = function(class,object)
  return getmetatable(object) == class
end

if _ENV.is==nil then _ENV.is = is end
return class