A val
doesn't take arguments, because it is computed and stored in a field. But I might just refer you to the extensive posts I did the last two days on the mailing lists.
Or, rather, let's consider it from a Java point of view, since Scala is compatible with Java at the jvm level, and it surely must obey jvm rules. Let's start with the first class:
abstract class X {
def expensiveOperation(p: Int => Boolean) : List[Int]
}
Now, let's extend it:
abstract class Y extends X {
override val expensiveOperation: ((Int) => Boolean) => List[Int]
}
So, from Java, we know that class X
has the method expensiveOperation
, which receives Function1[Int, Boolean]
and returns List[Int]
.
Now we go to class Y
. Naturally, it has to define the same method, but it also has to define the getter expensiveOperation
, which receives no arguments and returns Function1[Function1[Int, Boolean],List[Int]]
.
It might be workable, as long as this additional method didn't exist in X
too. So let's define it:
class Z extends Y {
override val extensiveOperation = new Function1[Function1[Int, Boolean], List[Int]] {
def apply(p: Int => Boolean) = List range (1, 10) filter p
}
}
How does that get defined? Does Scala copy apply
's body as a body for expensiveOperation
(the one receiving a parameter, not the getter one)? It might still be workable. Let's try something else, though:
class W(f: ((Int) => Boolean) => List[Int]) extends Y {
override val extensiveOperation = f
}
Now, how do we override the parameter-receiving extensiveOperation
? I suppose we could write it like this:
override def extensiveOperation(p: Int => Boolean) = extensiveOperation.apply(p)
That's workable. But I, personally, think it is a bit convoluted. My suggestion: write up a short SID, and get some agreement on a Scala mailing list. Without code to implement it, though, I don't think it has much chance of being adopted -- Scala has to track every function-typed val
to figure if it is overriding a def
or not.