Ankur
Ankur

Reputation: 27

Scala - Singleton Object inheritance

I have a working Scala application in production that is using a object which has several methods defined inside it.

There are new requirements for this application where I will have to rewrite (override) few of the methods from that object while reusing the definitions of remaining methods from that object.

How can I create a new object inheriting the original one so that I can override the definitions of a few selected methods?

Upvotes: 0

Views: 899

Answers (2)

Tim
Tim

Reputation: 27356

A Scala object cannot inherit from another Scala object so the obvious way is not possible.

If you can modify the original object then create a class that implements all the functionality and make the original object inherit from that class. Your new object can then inherit from the same class and override the methods that you want to change. However this will create two copies of any values in the base class, so it is not suitable for an object that contains a lot of data or does any one-off initialisation.

If you cannot modify the original object then you will have to copy all the methods of the first object in your new object. vals can be copied directly. defs can be copied using eta expansion:

def v = Original.v    // This is a simple value
def f = Original.f _  // This is a function value

Using def rather than val here will avoid storing multiple copies of the original values and will prevent lazy values from being computed until they are needed.

Using eta expansion will make f a function value rather than a method which may or may not be a problem depending on how it is used. If you require f to be a method then you will have to duplicate the function signature and call the original f:

def f(i: Int) = Original.f(i) // This is a method

Upvotes: 3

Andreas Neumann
Andreas Neumann

Reputation: 10894

My suggestion would be to move the code/logic to a trait or abstract class and have both objects extend these.

On the upside this would also give you better testability.

Another more hacky approach could be to not use the class/type system at all and jsut forward the methods using a new singleton objec:

scala> object A {def foo: String = "foo" ; def bar:Int = 0}
defined object A

scala> object B { def foo = A.foo; def bar = "my new impl" }
defined object B

scala> A.foo
res3: String = foo

scala> B.foo
res4: String = foo

scala> A.bar
res5: Int = 0

scala> B.bar
res6: String = my new impl

Upvotes: 0

Related Questions