Boost logo

Boost :

From: Giovanni Bajo (giovannibajo_at_[hidden])
Date: 2002-04-17 14:54:45


----- Original Message -----
From: "Douglas Gregor" <gregod_at_[hidden]>
To: <boost_at_[hidden]>
Sent: Wednesday, April 17, 2002 8:40 PM
Subject: Re: [boost] Loki Functor

> By "arbitrary function objects" I mean "any type that can be called like a
> function". It would be useful if we could have:
>
> void foo(Person&);
> void bar(Person);
>
> // ...
> std::list<Person> people;
> std::for_each(people.begin(), people.end(), foo+bar);
>
> That, of course, isn't going to happen because we can't just overload '+'
for
> every two types in the system :)
>
> And because we can't overload '+' for the general case, I think we
shouldn't
> overload '+' for just boost::function.

Ok, got it. I'm not sure I agree completely, after all we could just
overload operator+() as possible, where at least one parameter is the result
of bind() or a function<>, and just as an alternative syntax to a more
generic chain(). After all, lambda functions work only when you have a lamba
placeholder near-ish the begin of the function itself (see the famous "cout
<< "\n" << _1" example), so users are (or will be) already smart enough to
understand that overloaded operators work only if you have the right classes
around them.

Your example brings up also the issue with parameter chaining. From the code
you wrote, you expect that the results of chain(foo, bar) is a function
object that accepts a single parameter, which must be convertible to both
foo's and bar's parameter. I don't think this is a general enough solution,
since it couldn't handle cases where foo and bar have completely different
signatures. My proposal was to have chain(foo,bar) return a function objects
that must be called with all parameters of foo, followed by all parameters
of bar. The example above would have to be changed as:

for_each(people.begin(), people.end(), bind(chain(foo, bar), _1, _1));

Even if it makes your example more complex, it gives a total flexibility to
chain(), that's now able to chain any couple of function objects, just like
bind() is able to bind any parameter in any order.

Giovanni Bajo


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