4

I'm just getting started with Groovy, coming from a background of Haskell, C++ and a bit of Java.

Lets say I write a closure like the following:

def mult = { x, y -> x * y }

Later on I can then write mult(3,5).

But if I write mult(3), I get a compile error.

I could of course write mult.curry(3), but that seems a bit ugly to me.

So then I could try this approach:

def mult = { x -> { y -> x * y }}

Now, mult(3) works fine, but to multiply two numbers, I have to write mult(3)(5) to multiply two numbers.

What I want is the best of both worlds. I want to be able to write mult(3), mult(3,5) and mult(3)(5). Anyway to get closures to behave like this?

Clinton
  • 22,361
  • 15
  • 67
  • 163

1 Answers1

5

You could make something like this to "currify" your closure:

def currify(fn) {
    { Object... args ->
        if (args.size() == fn.maximumNumberOfParameters) {
            fn(*args)
        } else {
            currify(fn.curry(*args))
        }
    }
}

def mult = currify { x, y -> x * y }
def twice = mult(2)

assert mult(2, 5) == 10
assert twice(5) == 10
assert mult(2)(5) == 10
epidemian
  • 18,817
  • 3
  • 62
  • 71