[ANN] printable.lua

classic Classic list List threaded Threaded
5 messages Options
Reply | Threaded
Open this post in threaded view
|

[ANN] printable.lua

Dirk Laurie-2
A printable table is one that has a `__tostring` metamethod.  In a
well-designed object-oriented application, such a metamethod would be
provided as a matter of course.  In many cases, though, it is simply
not worth the effort.

For those cases, I've written a one-size-fits-all function that can be
used for that purpose.  It uses four reserved keys: `_sep`, `_fmt`,
`_kv` and `_post`, with inheritance via the `__index` metamethod to
achieve flexibility.

Sample:

    ptab = require "printable"
    S=ptab{msg='hello',1,2,{3,4}}
    print(S)
--> {1,2,{3,4},msg="hello"}
    A = {{1,2,3},{4,5,6}}
    latexmatrix = {{_sep=' \\\\\n',_post='%'},' & '}
    print (ptab(A,latexmatrix))
--> 1 & 2 & 3 \\
--> 4 & 5 & 6

<https://sites.google.com/a/aims.ac.za/experimental-mathematics/lua>

Dirk

Reply | Threaded
Open this post in threaded view
|

Re: [ANN] printable.lua

David Manura
On Mon, Nov 7, 2011 at 3:43 PM, Dirk Laurie <[hidden email]> wrote:
>    ptab = require "printable"
>    S=ptab{msg='hello',1,2,{3,4}}
>    print(S) --> {1,2,{3,4},msg="hello"}

A couple comments of my own ;)

(1) An alternative to making tables dumpable (by adding __tostring to
them) is to make `print` know how to dump tables:

  local pprint = require 'printable' . print
  S = {msg='hello',1,2,{3,4}}
  pprint(S) --> {1,2,{3,4},msg="hello"}
  -- and optionally replace `pprint` with `print` if you wish to always dump

Which is better?  It depends.  The latter avoids mutating tables and
adding extra `ptab` calls.  The former allows you to mark on the
tables themselves whether they get dumped.  Personally, I like to
mention such alternate design options in a "DESIGN NOTES" section of
the documentation.

(2) You might consider splitting this into two modules: one that dumps
tables to strings and one that adds a `__tostring` metamethod to
tables.  The former has already been explored at length (
http://lua-users.org/wiki/TableSerialization ), and being a bit lazy
I'd prefer not to go through the validation of this table dumping code
again to determine its qualities relative to others if I just want to
do the latter.  A user might want to use your table dumping
independent of the `__tostring` stuff, or the user might want to use
some other table dumper with your `__tostring` stuff.

(3) The module name `printable` is more restrictive than in practice.
Although you may pass the dumpable table to `print`, you might not
utilize `print` at all.  It's perfectly valid, for example, to pass
the dumpable table to `tostring` and store the result string in a
database without printing it.

(4) No need to `pcall(rawget,mt,'__tostring')` since `rawget` won't raise.

(5) LuaInspect tells me the various things: There's an undefined
global `_sep`, `local unpack` and `local load` are unused, there's an
extraneous tab char, `type` is not consistently localized like the
other functions (however, I tend to localize less than I used to and
might remove all the localization), and passing `ptab` as the first
argument to `init` which is the unused `dummy` suggests this argument
might simply be removed.

(6) It's best to avoid side-effects on module loading.  This includes
the top-level `io.stderr:write(idea..helphelp)`.  (Moreover, in some
cases, `io.stderr` might not be open.)

Reply | Threaded
Open this post in threaded view
|

Re: [ANN] printable.lua

Dirk Laurie-2
2011/11/8 David Manura <[hidden email]>:
> A couple comments of my own ;)
Thanks, these are really helpful.

> (1) Personally, I like to mention such alternate design options
> in a "DESIGN NOTES" section of the documentation.
I've got a 'warning' section, which says:
   The default custom settings have been chosen to "serialize" the table
   (i.e. to translate it to valid Lua code that will clone it) if that is
   reasonably possible.  Such serialization is not the main aim of the
   module…

But the idea of "DESIGN NOTES" is a good one for the future.  At this
stage it would suggest that more thought has gone into weighing
alternatives than would be justified.

> (2) You might consider splitting this into two modules: one that dumps
> tables to strings and one that adds a `__tostring` metamethod to
> tables.
See previous note: the main aim is the latter — the former is a mere
side effect.

> (3) The module name `printable` is more restrictive than in practice.
> Although you may pass the dumpable table to `print`, you might not
> utilize `print` at all.  It's perfectly valid, for example, to pass
> the dumpable table to `tostring` and store the result string in a
> database without printing it.
My first name [1] for what became this module was "gstring", short for
"generalized string".  It provoked some banter on its name but no
comments on the idea.  So I changed the name.

> (5) LuaInspect tells me the various things:
Thanks for the pointer.  I've just installed the Vim plugin. It's
clearly a great tool.

I agree with all your points, except this:
> passing `ptab` as the first
> argument to `init` which is the unused `dummy` suggests this argument
> might simply be removed.
It's required by the __call metamethod.  But yes, it's neater to pick
up ptab from the argument list, not from the local table.

> (6) It's best to avoid side-effects on module loading.  This includes
> the top-level `io.stderr:write(idea..helphelp)`.  (Moreover, in some
> cases, `io.stderr` might not be open.)
I asked about this in a previous thread.  I want the interactive user
to know how to get to the built-in help without reading the source
code.  Maybe us Lua programmers could agree that a module supplies
`mymod.help()` more often than not.

Thanks
Dirk

Reply | Threaded
Open this post in threaded view
|

Re: [ANN] printable.lua

Tom N Harris
In reply to this post by Dirk Laurie-2
On 11/07/2011 03:43 PM, Dirk Laurie wrote:
>
> <https://sites.google.com/a/aims.ac.za/experimental-mathematics/lua>
>

What is the license for this module?

Why do you put the option keys in the table, and not the metatable?

--
- tom
[hidden email]

Reply | Threaded
Open this post in threaded view
|

Re: [ANN] printable.lua

Dirk Laurie-2
2011/11/9 Tom N Harris <[hidden email]>:
> On 11/07/2011 03:43 PM, Dirk Laurie wrote:
>>
>> <https://sites.google.com/a/aims.ac.za/experimental-mathematics/lua>
>>
>
> What is the license for this module?
Thanks for pointing out the omission.  The information is now on the
webpage and will later appear in the code itself.  I've opted for the
same license as LÖVE:  the zlib/libpng license
<http://www.opensource.org/licenses/Zlib>.

>
> Why do you put the option keys in the table, and not the metatable?
>
That is a very good question. I've been waiting for it :-)

Apart from the retort "why not in the table?", there are two reasons.

1. It is easier for the user to access and change them.
2. Subtables inherit via the `__index` metamethod.

Both are not insuperable: access methods can be provided, and there is
no reason why metatables can't have metatables themselves.  If someone
can answer "why not?" cogently enough (e.g. by just going and doing
it), I'll consider that.

Dirk