Boost logo

Boost :

Subject: Re: [boost] [Phoenix] Some questions and notes...
From: Joel de Guzman (joel_at_[hidden])
Date: 2008-09-27 00:16:49


Giovanni Piero Deretta wrote:

>> Are you suggesting that you want phoenix functions to be "optionaly
>> lazy" too? Currently, they are not. That can be done, but I need
>> more convincing.
>>
>
> I would love if they were. But I can live with a layer on top of that.
> About the convincing part... hum I guess the only way is to try them
> and see if one find them convenient. For me it started as an
> experiment that worked.

Don't stop! Don't backout now that I'm starting to get convinced ;)
I know the value of your suggestion. I've actually pondered on this
a long time ago.

>>> I usually assume that an expression is not lazy unless I see a
>>> placeholder in the right position. I do not think that generic code
>>> makes thing worse: I carefully wrap all function parameters with the
>>> equivalent unlambda [1] *before* I pass them to higher order
>>> functions. In fact I always have to because in general I do not know
>>> if a certain function is optionally lazy or not.
>> This is exactly the problem I see with generic code.
>>
>
> In general the compiler will loudly tell you if you get something
> wrong (even if the errors might be unintelligible). Except of course
> for something like the example below...

Imperative code. Right.

[snip more on "optional-laziness"]

>>>>> Anyways, I can live with the current design, 'optional lazyness' could
>>>>> be built on top of phoenix lazy functions. My only compliant is that
>>>>> the 'lambda[]' syntax is already taken.

If we are to break the interface, I want to do it right.
Your feedback here is invaluable. The lambda[] behavior is
not set in stone, so to speak. I just want to be sure I'm
making the right decisions when changing the interface.
I cannot affort a failed experiment.

>> Those are pretty cool code. I'm still not sure of the implications
>> of all these though. I know for sure that people less smarter than
>> you are tend to get bitten by expressions that are intended to
>> be lazy but are actually immediate. Perhaps we can be arrange
>> for an "optionaly-lazy" layer on top of phoenix: it can be done,
>> phoenix is modular enough to have that layer.
>>
>
> It would be great.
>
>> In general though, I tend to avoid special cases. This
>> "optional laziness" is based on special casing depending
>> on some qualities of a lambda function.
>
> Well, I guess that is a point of view.. as I see it, functions are
> usually evaluated, unless some of the arguments are suspended: it is
> not eager evaluation that is special, but lazyness (or partial
> application or whatever you want to call it).

And it is a valid point of view. Recall in the brief introduction
that "The focus is more on usefulness and practicality than purity,
elegance and strict adherence to FP principles.". I do admire
people like you who embrace FP and pure functions. I try to
do as much FP as I can. But in the real world, it's C++ we
are dealing with with the side-effects, with the imperative
code, etc.

This is not the first time things like this are brought into light
though. As I said, I already pondered on this a long time ago.
I'm definitely interested with your approach. And, as someone
who already made progress in that route, I would love to collaborate
with you on having a facility like this built on top of phoenix.

> specific variable must be captured by reference? Lambda has it, but is
> a bit cumbersome:
>
> int i =0;
> var_type<int> r_i = var(i);
> (_1 + r_i)(0); //capture by ref
>
> something like this is desirable (and in fact can be done easily, but
> IMHO should be part of the library):
>
> byref<int> i = 0;
> (_1 + i)(0); // capture by ref

Phoenix has it but is not as terse. I think your suggestion
is good.

> BTW, yet another reason for always requiring lambda[] or something
> equivalent: the library could delay the decision of capturing by
> reference or by value by default up to the lambda introducer (I think
> I already mentioned something like this in the past):

Yes.

> int i = 0;
>
> lambda[ i+= arg1]; //default capture by value
> lambda_r[ i += arg1]; //default capture by reference
>
> It would make Phoenix similar to C++0x lambdas.
> Without requiring lambda[] [1] I do not see how this could be
> implemented (expecially if you want the default capture behavior to be
> by value).

I'm not sure about this one. What makes this better than
just having ref(i) ?

Regards,

-- 
Joel de Guzman
http://www.boostpro.com
http://spirit.sf.net

Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk