lua-users home
lua-l archive

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


On Nov 28, 2007 7:11 PM, John Dunn <John_Dunn@qscaudio.com> wrote:
[...]
> The main problem with this implementation is that there is no way to
> easily iterate the inputs and outputs. That makes it difficult to write
> generic scripts that could average any number of inputs, for example. I
> also think using the global namespace is pretty ugly as well.
[...]
> I don't like the idea that the inputs and outputs are global objects
> while the timer is a static module. My initial thought is to make a
> Controls module which contains 2 arrays, Inputs and Outputs.

A reasonable solution. I would add a bit of syntactic sugar:

print(object.value)  -- instead of object:getValue()
object.value = 42   -- instead of object:setValue(42)

by writing an adequate __index metamethod. The bonus of such a syntax,
beyond it's lightness, is abstraction over keys. That is, you can use
object[key] where key varies programmatically.

> Each scriptlet also has a single timer available to it. It's current
> implementation is as a module - a timer script might look something like
>
> count = 0
> -- count to 10 over and over again
> function onTimer()
>   count = count + 1
>   output_0:setValue( count )
>   if count == 10 then
>     count = 0
>   end
> end
>
> Timer.addEventHandler( onTimer )
> Timer.start( 1000 ) -- call every 1 second

I believe count should be declared in a local scope. This avoids
trouble when defining several handlers in a module. Likewise, onTimer
can be passed as an anonymous function since it is not referred to
elsewhere. So:

do
  local count = 0
  Timer.addEventHandler(function ()
    -- ...
  end)
end

This is clean but not very readable. And by the way, although the idea
behind the handler is very simple, you added the comment  "count to 10
over and over again" : the actual control structure feels a bit
awkward indeed.

Enter coroutines:

local wrap, yield = coroutine.wrap, coroutine.yield   -- locals are
easier, safer... and faster too !

Timer.addEventHandler(wrap(function()
  while true do
    for count = 1, 10 do  -- indeed "count to 10 over and over again"
      -- ...
      yield()
    end
  end
end))

Here the control structures are very natural, even though the function
is actually executed by slices. Also, the scope of count is now as
narrow as possible. For these reasons, I would favour the use of
coroutines in such a setup.

--
-- Thomas