我想实现一个类C
来存储各种数字类型的值,以及布尔值。此外,我希望能够在此类的实例上、在类型之间进行操作、在必要时进行转换Int --> Double
,即Boolean -> Int
能够添加Boolean + Boolean
、、、、Int + Boolean
等Boolean + Int
,尽可能返回最小的可能类型(或)。Int + Double
Double + Double
Int
Double
到目前为止,我想出了这个:
abstract class SemiGroup[A] { def add(x:A, y:A):A }
class C[A] (val n:A) (implicit val s:SemiGroup[A]) {
def +[T <% A](that:C[T]) = s.add(this.n, that.n)
}
object Test extends Application {
implicit object IntSemiGroup extends SemiGroup[Int] {
def add(x: Int, y: Int):Int = x + y
}
implicit object DoubleSemiGroup extends SemiGroup[Double] {
def add(x: Double, y: Double):Double = x + y
}
implicit object BooleanSemiGroup extends SemiGroup[Boolean] {
def add(x: Boolean, y: Boolean):Boolean = true;
}
implicit def bool2int(b:Boolean):Int = if(b) 1 else 0
val n = new C[Int](10)
val d = new C[Double](10.5)
val b = new C[Boolean](true)
println(d + n) // [1]
println(n + n) // [2]
println(n + b) // [3]
// println(n + d) [4] XXX - no implicit conversion of Double to Int exists
// println(b + n) [5] XXX - no implicit conversion of Int to Boolean exists
}
这适用于某些情况 (1, 2, 3),但不适用于 (4, 5)。原因是类型从低到高隐式扩大,但不是相反。在某种程度上,方法
def +[T <% A](that:C[T]) = s.add(this.n, that.n)
不知何故需要有一个看起来像这样的合作伙伴方法:
def +[T, A <% T](that:C[T]):T = that.s.add(this.n, that.n)
但这不会编译有两个原因,首先编译器无法转换this.n
为类型T
(即使我们指定了视图绑定A <% T
),其次,即使它能够转换this.n
,在类型擦除之后这两种+
方法变得模棱两可。
对不起,这么久。任何帮助将非常感激!否则,我似乎必须明确写出所有类型之间的所有操作。Complex
如果我必须添加额外的类型(菜单上的下一个......),它会变得很棘手。
也许有人有另一种方法来完全实现这一切?感觉好像有一些简单的东西我忽略了。
提前致谢!