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

Re: ICFP - OCaml entry



In article <Pine.BSF.4.21.0009010814230.24436-100000@shell5.ba.best.com>, 
Brian Rogoff <bpr@shell5.ba.best.com> wrote:


> On Fri, 1 Sep 2000, Bruce Hoult wrote:
>> Oh, I'm a lot happier than that with our effort.
>
> Congratulations. I'm impressed that a distributed team could work on a
> short time scale project like that.

Thanks. For my part, I am living in Germany and had contact with Bruce till
noon and after midnight, and with Jeff in the afternoon and in the evening.
My part was the GML compiler, simplifier and optimizer (partial evaluator).
I could work perfectly in isolation, after giving Bruce my informal
specification, what I await from the lexer (<list> of (<integer> or
<double-float> or <byte-string> or <symbol> or <character>)).
When I started sunday 13:00 GMT, the lexer was ready, but did not yet
produce this format. I did not care, because I could use literal lists as my
test phrases. In the evening I had a working compiler that was integrated by
Bruce the next morning, and monday night I added the optimizer. Just look at
the cvsweb at the compiler. It is in Engine.dylan

>
>> In terms of the expressiveness of Dylan vs OCaml as languages with which
>> to express solutions to complex problems I couldn't be more delighted.
>
> Could you be more precise? What features of Dylan do you think give you an
> expressiveness advantage over OCaml? I'm not looking to start a language
> flame war, I just find language comparisons interesting. I certainly
> consider Dylan a true FP (first class functions, block structure with
> lexical scope, that's an FP!)

I certainly could put the purely functional subset of Dylan to best use,
because of the pleasantly regular semantics of GML. I do not use a single
assignment in my code!

Looking at the lines you will see frequent use of syntax-driven macros, that
helped to keep the details to a minimum and emphasize the essence. For
example math primitives are introduced thus:

define unary-primitive floor(<fp>) end;

or

define numeric-binary-primitive add(\+) end;

The macro expansions also produce the definitions that are also used by the
simplifier and the partial evaluator. The latter line introduces the GML
operators addi on <integer>s and addf on <double-float>s. Of course the
macro definitions grew as the optimizer matured, while the macro invocations
remained the same.

The real power however comes from multiple dispatch. This is a
pattern-matcher on steroids, because more specific methods of a generic
function inherit all the power of the less specialized ones.
The optimizer basically operates by examining the front portion of the GML
program and the methods of the optimizable-{one, two, three} methods get the
chance to either rewrite that portion by compile-time evaluating it, or can
return a fragment containing the partially applied code.

The optimizer is incredibly flexible, because specializations can be added
by macros or by hand if there is a need. Sadly, I could not add all
optimizations that I conceived (esp. the "empty array", "constant function"
and "constant before binding" ones) because of time constraints, testing
overhead and the observation that the renderer is the most time critical
part. However I plan to put these optimizations into the CVS tree too, and I
do not expect that it will take more than a couple of minutes!

All syntactic and semantic errors are caught by the use of type contraints
and are reported by a top-level handler.

So I regard Dylan as an ideal language for this kind of tasks, where rapid
prototyping and the final delivery are only separated by hours.

I hope this gave a glimpse of it.

    Gabor


>
> -- Brian



Follow-Ups: