Wither Self (longish)

Chris Pressey cpressey@REDACTED
Wed Sep 10 18:35:37 CEST 2003


On Wed, 10 Sep 2003 16:07:58 +0200
"Vlad Dumitrescu" <vlad_dumitrescu@REDACTED> wrote:

> I guess I am biased by some real-life examples I met, where the
> inlined function was a real monster and should have been split in 2 or
> maybe 3 different simpler functions, the result still being easier to
> read than the original. Think just of 20 lines with an indentation of
> 50+ chars... *brrr*

Having been the author of some funs like this, I concur.  But there is a
tradeoff - in my case, I have a function that creates a lot of callback
functions (for GTK.)  The easiest way to get certain parameters to those
callback functions is to have the callbacks be declared as funs so that
they can access the bindings in the main function.  The other way to do
it would be to pass those bindings as parameters - the GTK callbacks
certainly allow this, but after trying it, my judgement call was that it
was even messier that way.  So I stuck with a really long main function
with lots of embedded funs - and this is where SciTE (the folding editor
that groks Erlang syntax) has really helped.

There are of course more ways to deal with it.  For example, factor
everything that doesn't need to inherit bindings out of the fun, into
utility functions.

But my needs have become even more involved lately, which is why I'm
currently pondering lambda modules and their alternatives.  (I've
foregone considering hot code replacement on them because it's just too
damn hard, if it's indeed possible.)

My 'problem' is this.  Behaviours are a great way to structure your
code.   But the more behaviours and callback modules I write, the
simpler I tend to make them, to the point where the callback contains
mostly data and hardly any code.  This certainly seems like good
engineering - the behaviour does most of the work (making it 'reusable',
etc) while the callback mainly tells the behaviour how, specifically, it
should do the work.

But then I get to the point where I'd like to make tiny alterations in a
callback module, *from my code*.  And the callback modules are simple
enough, at this point, that they *could* just be data structures.

Unfortunately, if I convert the callback module to a data structure,
many nice things can disappear.  Essentially, all the callbacks which
aren't just plain data, have to become funs, and this introduces some
inconveniences that look minor, but can be very annoying.  For example,
calls that were once sweet and simple like
  M:f(A1, A2)
now have to become something like
  dict:fetch(f, M)(A1, A2)
and so on.  Initially it looked like a great advantage would be that I
could store these 'callback modules' in file:consult/1 format - but
file:consult/1 doesn't allow for funs, so I wrote a version of it that
does (I've attached it to this e-mail for the sake of curiousity.)

All in all it's a slight win, because I can now manipulate and transform
the callback 'module', in my code - but it's only a *slight* win,
because the structure is now not nearly as nice as it was when it was a
genuine behaviour-conforming callback module.

Anyway - that's been my experience so far.  I'd like to figure out a way
for it to be a big win, or at least a medium-sized win, instead, but I
think it'll mean getting in up to my elbows in parsing and evaluating
Erlang code, and maybe even a parse transform to handle M:f(A) when M is
not a 'real' module - which sounds like more trouble than it's worth...

-Chris
-------------- next part --------------
An embedded and charset-unspecified text was scrubbed...
Name: consult.erl
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20030910/0309719f/attachment.ksh>


More information about the erlang-questions mailing list