I am implementing some lightweight mathematical vectors in scala. I would like to use the type system to check vector compatibility at compile time. For example, trying to add a vector of dimension 2 to another vector of dimension 3 should result in a compile error.
So far, I defined dimensions as case classes:
sealed trait Dim
case class One() extends Dim
case class Two() extends Dim
case class Three() extends Dim
case class Four() extends Dim
case class Five() extends Dim
And here is the vectors definition:
class Vec[D <: Dim](val values: Vector[Double]) {
def apply(i: Int) = values(i)
def *(k: Double) = new Vec[D]( values.map(_*k) )
def +(that: Vec[D]) = {
val newValues = ( values zip that.values ) map {
pair => pair._1 + pair._2
}
new Vec[D](newValues)
}
override lazy val toString = "Vec(" + values.mkString(", ") + ")"
}
This solution works well, however I have two concerns:
How can I add a
dimension():Int
method that returns the dimension (ie. 3 for aVec[Three]
)?How can I handle higher dimensions without declaring all the needed case classes in advance ?
PS: I know there are nice existing mathematical vector libs, I am just trying to improve my scala understanding.