tags:

views:

46

answers:

2

Here is an example:

int[] arr = [ 1, 2, 3, 4, 5 ];
auto foo = filter!("a < 3")(arr);
assert(foo == [ 1, 2 ]); // works fine

Now I want to be able to parameterize the predicate, e.g.

int max = 3;
int[] arr = [ 1, 2, 3, 4, 5 ];
auto foo = filter!("a < max")(arr); // doesn't compile

This snippet won't compile obviously, sine the filter!()'s predicate only accepts one parameter. Is there a way to overcome this limitation without resorting to the good ol' for/foreach loop?

+2  A: 

The string lambdas are just a library level convenience, designed to be even terser than D's builtin function/delegate/template literals as a convenience. Here's what to do when you need more power:

Note: The following should work, but may behave erratically at the time of writing due to compiler bugs.

import std.algorithm;

void main() {
    int max = 3;
    int[] arr = [ 1, 2, 3, 4, 5 ];
    auto foo = filter!((a) { return a < max; })(arr);
}

The following actually does work:

import std.algorithm;

void main() {
    int max = 3;
    int[] arr = [ 1, 2, 3, 4, 5 ];
    auto foo = filter!((int a) { return a < max; })(arr); 
}

The difference is whether a type is explicitly specified.

dsimcha
I'd edit your post, but still working on the rep. You should modify the comment on your second example.
he_the_great
@he_the_great: Actually both compile. That comment came from me copying/pasting from the OP and forgetting to strip that comment. Fixed now, though.
dsimcha
+2  A: 

In addition to dsimcha's answer, you can also use a local function if you like:

int max = 3;
bool pred(int a) { return a < max; };
int[] arr = [1, 2, 3, 4, 5];
auto foo = filter!(pred)(arr);
Peter Alexander