[Date Prev][Date Next][Thread Prev][Thread Next]
[Date Index]
[Thread Index]
- Subject: Re: Safe navigation operator
 
- From: "Juris Kalnins" <juris@...>
 
- Date: Mon, 23 Aug 2010 16:06:39 +0300
 
On Mon, 23 Aug 2010 15:45:25 +0300, Cuero Bugot  
<cbugot@sierrawireless.com> wrote:
> local emptytable = {}
> local function Opt (t) return t or emptytable end
>
>   if config.Opt(network).Opt(server).url then
>     dosomething(config.network.server.url)
>   End
That does not make any sense. I do not know what I was thinking. Sorry
for the noise...
Well at least it illustrate what I meant by 'context'. Opt() is "in the  
middle path/table traversal" while the last ".url" is "the final  
access". If metamethods __index / __newindex did provide this kind of  
information then  it would be easy to implement safe navigation operator  
with metatables
Would that be something completely unrealistic to provide more  
contextual information as parameters of the __index / __newindex  
metamethods ?
If you don't care about perfomance, ...
======8<============================
v = {}
mt = {
    __index = function (t, k)
        local key
        local ret = {}
        if t and rawget(t, "_key") then
            key = t._key
            ret._container = t._container
        else
            key = {}
            ret._container = t
        end
        key[#key + 1] = k
        ret._key = key
        setmetatable(ret, mt)
        return ret
    end,
    __newindex = function (t, k, v)
        local key
        if t and rawget(t, "_key") then key = t._key else key = {} end
        key[#key + 1] = k
        io.write("assign ", v, " to")
        local sep = ' '
        for n,i in ipairs(t._key) do
            io.write(sep, i)
            sep = '.'
        end
        io.write(" in ", tostring(t._container), "\n")
    end
}
setmetatable(v, mt)
v.a.b.x.y.n.m = 1
======>8============================
Basically, you create proxy object that builds expression tree it is  
passing through
(in this case, navigation path), and use __newindex as a trigger for  
needed action.
To access value, you need to define all sorts of __eq, __tostring, etc  
methods that
vould return configuration value pointed to by the proxy.
Being able to handle chains of operations in a single metamethod would  
really simplify
such cases, e.g., to have
__newindex(container, value, key, ...)
But I do not see how it is possible to add this without making it  
imcompatible with
existing code.