Ruby-style "each" in D?

Simen Kjærås simen.kjaras at gmail.com
Thu Mar 20 08:02:17 PDT 2014


On 2014-03-20 14:16, Andrea Fontana wrote:
> On Thursday, 20 March 2014 at 12:32:49 UTC, w0rp wrote:
>> // std.parallelism parallel function here.
>> someRange.whatever.parallel(numberOfUnits).each!doSomething
>
> +1
>
> This works:
> foreach(i; [0,1,2,3,4,5].parallel) i.writeln;
>
> This works:
> [0,1,2,3,4,5].each!writeln;
>
> This won't compile:
> [0,1,2,3,4,5].parallel.each!writeln;
>
> Error: template tmp.each cannot deduce function from argument types
> !(writeln)(ParallelForeach!(int[])), candidates are:
> /tmp/tmp.d(9):        tmp.each(alias fun, Range)(Range range) if
> (isInputRange!Range)


It could be made to work, though:

template isIterable(T) {
     enum isIterable = is(typeof((T t){foreach (e; t){}}));
}

template isRefIterable(T) {
     enum isRefIterable = is(typeof((T t){foreach (ref e; t){}}));
}

void each(alias fun, Range)(Range range)
     if (isInputRange!Range)
{
     while (!range.empty)
     {
         unaryFun!fun(range.front);
         range.popFront();
     }
}

void each(alias fun, Range)(Range range)
     if (!isInputRange!Range && isRefIterable!Range)
{
     foreach (ref e; range) {
         unaryFun!fun(e);
     }
}

void each(alias fun, Range)(Range range)
     if (!isInputRange!Range && isIterable!Range && !isRefIterable!Range)
{
     foreach (e; range) {
         unaryFun!fun(e);
     }
}

void main() {
     [0,1,2,3,4,5].parallel.each!writeln;
}

--
   Simen


More information about the Digitalmars-d mailing list