Alan Manuel Gloria:
>Instead of doing *any* infix fixing in the reader at all, why not just 
>delegate the whole mess of infix-fixing to the macro? i.e. sweet-read() sees 
>{foo bar batz}, it outputs (infix-macro foo bar batz)

One problem with that is that macros will see DIFFERENT things depending on 
where they are placed.  (Well, _I_ see this as a problem.).  E.G., in:
 egg
   nfx
     ham
       3 + 4

If egg, nfx, and ham are all macros that recurse deeply on their arguments, 
then egg and ham will "see" different versions of 3 + 4; one will see (3 + 4) 
and the other (+ 3 4).  This makes macro processing potentially 
nasty/complicated.  Macro processing can be complicated enough!  If the program 
were more deeply nested (say, with a cond or if and a function call 
intervening) and/or you didn't even KNOW that something was implemented by a 
macro, it could be even worse.

Obviously, whether or not you REALLY consider this a problem depends on what 
the macros do.    But it appears to me to make macro-processing WAY more 
complicated.

By moving infix processing into the reader, suddenly there are NO special 
rules; _all_ macros see _only_ the normal s-expressions, and there are NO other 
alternatives.  All macros work "as-is", and possibly more important, you don't 
have to do detailed reasoning about what the macros will see.  They'll see the 
same thing they always saw: operators first, in EVERY s-expression, without 
exception.

That doesn't mean infix processing at the reader is the One True Way; it's a 
trade-off.  But at least maybe you see why I decided to trade in that direction.


> Declaring a "pattern" to match a string from an input stream just feels so 
> Perlish, to me.... the infix pattern [should be changeable]...  I (or 
> someone) might make a "convoke" (or something) infix operator...

My explanation may be too Perlish.  The rule is actually simple, it's basically 
"1 to 5 of these punctuation characters..." plus a few special cases.  Perhaps 
I should rewrite the pattern rule without using a regex.

I think allowing developers to declare operators is a good thing for a _macro_. 
 But if you do infix processing at _READ_ time, I think requiring it is a bad 
idea.  That would create nasty read-ordering dependencies; if you read an 
expression, and THEN read the command that defined a new operator, it wouldn't 
work as expected.

Many languages seem to intentionally devise their infix operators so that they 
are only punctuation anyway (with possible exceptions for "and' and "or").  
That way, all infix operators are visually distinct, and being visually 
distinct is a good thing anyway.  So I don't think the limitation is a big 
deal.  You can have a convoke operator, you just can't spell it as "convoke" 
:-).



> But if (...) will only be used to surround "strict s-expressions", and [...] 
> force "no infix" interpretation, then this is no longer a problem.
Hmm, I thought {} for "infix interpretation", everything else being no infix? 
It seems in most of your later samples, {} is used around infixes.

No, the default in sweet-expression is "infix everywhere", and I was thinking 
about specific ways to turn it off.  You can even see this in my first example 
(the factorial) at http://www.dwheeler.com/readable/ :

 defun factorial (n) 
   if (n <= 1)
       1
       n * factorial(n - 1)


Note that the "n * factorial..." didn't get surrounded by {...}.  Note also 
that factorial(n - 1) isn't surrounded by {...}, but name-prefixing ITSELF also 
permits inside it.

The rationale for this is pretty straightforward: In nearly all other 
languages, infix is the DEFAULT.  So, I set up infix to be the default 
everywhere too.  Sometimes you don't WANT it to be the default, so I used as(+) 
to escape it.

But if I'm going to switch to using {...} instead of (..) for grouping infix 
anyway, then it's certainly plausible to say something like "for infix, must 
surround with {...} or name-prefixed function name".  This would mean that 
where indentation is relevant, infix is NOT enabled; you'd have to use {...} or 
name(...) to have an infix use.

The example would become:
 defun factorial (n) 
   if {n <= 1}
       1
       {n * factorial(n - 1)}

The {...} would a good idea if the reader inserted a macro call here.  But if 
not, I'm not sure what the advantage would be.  Anyone think this is a big boon 
(e.g., to warn that infix processing might happen here)?  I guess it would 
eliminate the need for a "no prefix" operator, but other than that, is there 
any reason to do so?

>Just thought to mention it, but pg's Arc intends to use (a b) for a[b], for 
>the logical reason that a mapping collection is equivalent to a mapping of 
>objects of one type to another (i.e. a function).

Very interesting, thanks for the pointer.  Sweet-expressions already convert 
a(b) to (a b), so I don't see the point of doing the same thing with a[b].  Of 
course, f[1 2 3] isn't TOO bad as a notation for function calls, so if the idea 
was to reserve (...) SOLELY for their traditional s-expression purpose, and use 
f[1 2 3] for calls, THEN they make sense.  Arc has more freedom to manipulate 
syntax than I do, since my goal is to create something that can work with 
EXISTING systems.

--- David A. Wheeler 


Reply via email to