[Date Prev][Date Next][Thread Prev][Thread Next]
- Subject: Semantics and implementation. Was Re: Rici tries to explain. Was Re: Arguments by reference?
- From: Rici Lake <lua@...>
- Date: Fri, 2 Sep 2005 13:56:18 -0500
On 2-Sep-05, at 1:35 PM, William Trenker wrote:
On 9/1/05, Rici Lake <email@example.com> wrote:
Let's trust the implementers to worry about
the low-level stuff, and get it right. We can just think about the
semantics, and how to write beautiful programs with that.
Agreeing wholeheartedly, may I pick a nit? Aren't there some
high-level semantics that can be derailed when the programmer has no
option but to work too close to the details? A simple example is
testing for an empty table.
Actually, this is a semantic question. What is the table? How is empty
If the table is being used as a vector, and the vector is known to be
dense (i.e. there are no internal nils), then the test is easy:
if t == nil then ...
This deliberately avoids testing for "emptiness", because I might be
storing metadata in the table which does not affect emptiness. (For
example, I might have chosen to set t.n to 0, in which case I could
also check to see if t.n was 0 :)
If the table is a dictionary, then the standard way of testing would be
next(t). I often put:
local hasdata = next
at the top of my code to make that particular test more readable.
But in some applications, I might only care about certain table keys
and not other ones. In other applications, the table might be non-empty
even if it has no direct data, because it has been indirected with an
__index metamethod to another table. So in those cases, I would have to
construct my own appropriate test for emptiness.
These different mechanisms are not competing on efficiency. They are
competing on semantic correctness. In general, with a few exceptions,
you'll find that the least contrived way of doing something is the
fastest, in any scripting language, because the cost of interpretation
(even VM interpretation) plus the cost of function calls (or the
"C/scripting frontier", if you prefer) tends to outweigh other
Once you have a working program, you can certainly start thinking about
efficiency. But even there, I would say your first steps are:
1) use a good algorithm
2) use data structures and control flow structures which co-operate
well with Lua.
(By the way, the fastest test for empty on a dense vector is the t =
nil test, but if you're tracking the vector size anyway, t.n == 0 is
slightly faster. However, it's not worth tracking vector size just for
the sake of that test; you would only do it if the vector was sparse in
which case table.getn doesn't give you reliable results, at least in