std.algorithm missing for_each?

Idan Arye GenericNPC at gmail.com
Wed Feb 5 04:18:14 PST 2014


On Wednesday, 5 February 2014 at 12:08:11 UTC, Jens Mueller wrote:
> Jakob Ovrum wrote:
>> On Wednesday, 5 February 2014 at 10:03:52 UTC, Jens Mueller 
>> wrote:
>> >Dear lovely D community,
>> >
>> >recently I refactored some code into component style (see
>> >Component
>> >Programming in D by Walter
>> >http://www.drdobbs.com/architecture-and-design/component-programming-in-d/240008321)
>> >
>> >It looks about like this
>> >
>> >someInputRange
>> >.filter!()
>> >.map!()
>> >
>> >Next I want to discard all elements but perform some last
>> >operation on
>> >each element. The problem is that map forces me to pass a 
>> >function
>> >that
>> >returns. Of course I could return a fake value. But that 
>> >doesn't
>> >look
>> >proper. Another option is to iterate using the foreach loop. 
>> >Does
>> >not
>> >look better either, does it?
>> >
>> >This makes me believe that std.algorithm misses an algorithm. 
>> >The
>> >for_each algorithm (see for_each in STL
>> >http://www.cplusplus.com/reference/algorithm/for_each/).
>> >
>> >To rephrase the problem more general (because maybe I'm just 
>> >not
>> >seeing
>> >how to fit the pieces together): How do you perform some 
>> >arbitrary
>> >operation on the elements of a range?
>> >
>> >myRange
>> >.each!((e)
>> >{
>> >	e.someOperation();
>> >});
>> >
>> >Jens
>> 
>> Consuming an input range in the functional style should be 
>> done by
>> std.algorithm.copy (passing an output range) or by simply 
>> passing
>> the input range to the consumer algorithm.
>> 
>> Sometimes this isn't possible, which means reverting to 
>> foreach,
>> i.e. a mix of functional and imperative style. This is the
>> equivalent of STL's `for_each`.
>> 
>> I think adding an `each` function to Phobos is problematic. It 
>> is
>> syntax sugar for foreach, but with the downside of obfuscating 
>> what
>> is essentially imperative code. IMO, imperative code should 
>> look
>> like imperative code, which with foreach is by no means ugly.
>
> Rephrasing your words to get a clear image for myself: You 
> argue that
>
> foreach (e; someInputRange
>             .filter!()
>             .map!())
> 	e.someOperation();
>
> is not ugly and the way to go.
>
> And
>
> someInputRange
> .filter!()
> .map!()
> .each!();
>
> is bad because it mixes two styles.
>
> Jens

Your `foreach` is ugly because you need to look closely to see 
the boundary between the functional chain and the iterative 
execution.

In this case, adding a block makes things much more elegant:


     foreach (e; someInputRange
                .filter!()
                .map!())
     {
             e.someOperation();
     }


More information about the Digitalmars-d mailing list