[Date Prev][Date Next][Thread Prev][Thread Next]
[Date Index]
[Thread Index]
- Subject: Re: getfenv question
- From: RLake@...
- Date: Thu, 18 Dec 2003 11:04:19 -0500
Mark Hamburg preguntó:
> Is there a way other than wrapping things in pcall to tell what the
maximum
> level I can pass to getfenv is?
> I'm trying to implement pseudo-dynamic scoping by searching up the call
> chain for the first function environment referencing a particular
variable.
This seems like a very slow way of implementing dynamic scoping. Why don't
you do something like this:
do
local dynvars = {}
setmetatable(getfenv(), {
__index = dynvars,
__newindex = function(t, k, v)
if dynvars[k] ~= nil then
dynvars[k] = v
else
rawset(t, k, v)
end
end
}
local function propagate(dv, val, okflag, ...)
dynvars[dv] = val
if okflag then return unpack(arg)
else error(args[1])
end
end
function with(dv, val, fn, ...)
local old
old, dynvars[dv] = dynvars[dv], val
return propagate(dv, old, pcall(fn, unpack(arg))}
end
end
The syntax for with is going to be a bit of a pain, but you could
macro process:
with var = val do ... end
into
with("var", val, function() ... )
And, actually, if you were only going to use that syntax,
you could simplify the definition of with :
function with(dv, val, fn)
local old
old, dynvars[dv] = dynvars[dv], val
local okflag, err = pcall(fn)
dynvars[dv] = old
if not okflag then error(err) end
end
It actually would not be that hard to implement that in the
Lua parser.