0
votes

I am attempting to extend the idea of using value classes for type safety as described here http://docs.scala-lang.org/overviews/core/value-classes.html to a more abstract version that allows implicit conversions. For example, I have some Measure trait

trait Measure {
implicit def +[B <: Measure](other: B): Measure
val value: Double
}

and some implementations

//this will compile because [_ , Meters] is not ambiguous since
//for this example im only using one conversion. see below


case class Meters(value: Double) extends Measure {
   def +[B <: Measure](other: B): Meters = Meters(other.value * implicitly[Converter[_ , Meters]].factor + this.value) }
case class Fathoms(value: Double) extends Measure {
   def +[B <: Measure](other: B): Fathoms = Fathoms(other.value * implicitly[Converter[_ , Fathoms]].factor + this.value) }

and a converter trait and implementation for the implicit lookup mechanism to find

trait Converter[F, T]{
  val factor: Double
}
implicit object Meter2Fathom extends Converter[Meter, Fathom]{
  val factor: Double = .556
}
implicit object Fathom2Meter extends Converter[Fathom, Meter]{
  val factor: Double = 1.8
}

Is there a way to define Converter implementations on "whatever B is"? I want run time error if we try to add together two measures for which there doesnt exist a conversion factor, but still be able to compile.

//will not compile of course. the idea is to somehow reify whatever B 
// is and look that implicit converter up, instead of actual B.
case class Meters(value: Double) extends Measure {
  def +[B <: Measure](other: B): Meters = Meters(this.value + other.value * implicitly[Converter[* B *, Meters]].factor
1
General design solution for these type of problems is to assume one representation of Measure to be standard.. lets say Meter. And all... other Measure will implement a toStandard or toMeter and fromStandard or fromMeter function. Now do all... calculations in Meter... then convert to that Mesure by using fromMeter.sarveshseri
Other more functionally pure but advanced method can be to use adhoc-polymorphism with Type-classes... a very good read on Type-classes -> danielwestheide.com/blog/2013/02/06/…sarveshseri
This is probably the way to go. one more computation step in the conversion alleviates need of having n^2 conversion factors. +1Azeli

1 Answers

0
votes

As far as I understood what you want is magnet pattern. There is an extensive blog here: http://spray.io/blog/2012-12-13-the-magnet-pattern/