lazy redux

Michel Fortin michel.fortin at michelf.com
Sun Dec 6 10:14:19 PST 2009


On 2009-12-06 10:44:17 -0500, Andrei Alexandrescu 
<SeeWebsiteForEmail at erdani.org> said:

> Tim Matthews wrote:
>> Andrei Alexandrescu wrote:
>>> Should we sack lazy? I'd like it to have a reasonable replacement. 
>>> Ideas are welcome!
>>> 
>>> Andrei
>> 
>> According to the doc page: 
>> http://www.digitalmars.com/d/2.0/lazy-evaluation.html
>> you (and/or Tomasz Stachowiak) were the one who suggested it in the 
>> first place. How'd it go for you? :)
> 
> Well the story is, I suggested something very different, namely 
> automatic conversion of expressions to delegates, i.e.:
> 
> void fun(int delegate() dg) { ... }
> 
> int a;
> fun(a += 5); // works, same as fun({ a += 5; });
> 
> I am not sure about how good that idea is, but anyway on top of it 
> Tomasz suggested defining a storage class for that, which (1) takes 
> matters to a completely place, (2) marks a sharp decline in the quality 
> of the feature. I protested the addition of "lazy" very strongly in a 
> subsequent post. Since I was relatively new in the newsgroup and the 
> rant bordered on an ad hominem attack against Tomasz, it earned me a 
> good amount of negative goodwill (and for good reasons). If I remember 
> correctly, the flamewar that ensued in my leaving the newsgroup for a 
> good while. I'm very glad the atmosphere has improved so much since - 
> back then it was often some sort of a turf war.
> 
> Anyhow, if we leave the feature as an implicit conversion expression -> 
> delegate or function, I think the whole thing is sound (contingent on 
> probably taking care of a couple of corner cases). The remaining 
> problem is that fun(gun()) does not always evaluate gun(), even though 
> the reader who is unaware or forgot about the conversion thinks 
> otherwise. If we require fun({gun();}), the notation is more awkward 
> but also clarifies to the reader what's happening.
> 
> My take is this: since assert() establishes a precedent, I'd hate that 
> to be magic inaccessible to mere mortals. Functions like enforce() and 
> logging frameworks can make good use of the feature.

That's what I'd do too.

But I think we could improve lazy by splitting it in two. The first 
would work as it does today, allowing things like enforce(). The second 
could be less intrusive by having no semantic implications for the 
caller. The idea is simple: force purity on it. This way, the caller 
doesn't have to think about whether or not an argument is a lazy one or 
not. Suggested syntax:

	void logIfFalse(bool condition, pure lazy string message);

	logIfFalse(i == 1, createMessage());

If the expression "createMessage()" is pure, then it'll be evaluated 
lazily. Otherwise it should be evaluated in advance (like normal 
parameters) and a delegate returning the result should be given to the 
function.

This would make it mostly a cross-function manual optimization 
mechanism. The called function can assume its "pure lazy" delegate is 
pure and optimize things accordingly. If you have a couple of functions 
passing themselves a "pure lazy" argument like that, a good optimizer 
could make sure it is never is evaluated more than once even across 
function boundaries.

-- 
Michel Fortin
michel.fortin at michelf.com
http://michelf.com/




More information about the Digitalmars-d mailing list