I'm not quite sure what restrictions are imposed on you, for example, which classes should / should be private, but using F-limited polymorphism can be a step towards your desired solution.
abstract class Point[P <: Point[P]] { def +(that: P): P } class PointInt(val x:Int,val y:Int) extends Point[PointInt] { def +(that:PointInt) = new PointInt(this.x + that.x, this.y + that.y) } class PointDouble(val x:Double,val y:Double) extends Point[PointDouble] { def +(that:PointDouble) = new PointDouble(this.x + that.x, this.y + that.y) } object Point { def apply(x:Int,y:Int) = new PointInt(x,y) def apply(x:Double,y:Double) = new PointDouble(x,y) } val a = Point(1,2) val b = Point(3,4) val c = a+b
Please note that this will not help you if you want to hide your implementations, i.e. make them private and declare public interfaces using only a common Point , as others have already pointed out.
source share