也许你可以包装一个Map [Manifest,Any],确保这些值对应于清单键。
可能的草图。首先一个小帮手
class Typed[A](value: A)(implicit val key: Manifest[A]) {
def toPair: (Manifest[_], Any) = (key, value)
}
object Typed {
implicit def toTyped[A: Manifest](a: A) = new Typed(a)
implicit def toTypable[A](a: A) = new {
def typedAs[T >: A : Manifest] = new Typed[T](a)(manifest[T])
}
}
然后包装本身(这是不是一个地图)
class TypedMap private(val inner: Map[Manifest[_], Any]) {
def +[A](t: Typed[A]) = new TypedMap(inner + t.toPair)
def +[A : Manifest](a: A) = new TypedMap(inner + (manifest[A] -> a))
def -[A : Manifest]() = new TypedMap(inner - manifest[A])
def apply[A : Manifest]: A = inner(manifest[A]).asInstanceOf[A]
def get[A : Manifest]: Option[A] = inner.get(manifest[A]).map(_.asInstanceOf[A])
override def toString = inner.toString
override def equals(other: Any) = other match {
case that: TypedMap => this.inner == that.inner
case _ => false
}
override def hashCode = inner.hashCode
}
object TypedMap {
val empty = new TypedMap(Map())
def apply(items: Typed[_]*) = new TypedMap(Map(items.map(_.toPair) : _*))
}
有了,你可以做
import Typed._
val repository = TypedMap("foo", 12, "bar".typedAs[Any])
库:TypedMap =地图(Java .lang.String - > FOO,INT - >如图12所示,任一 - > 巴)
您检索元素与
repository[String] // returns "foo"
repository.get[Any] // returns Some("bar")
我认为私有的构造应确保_ asInstanceOf
是安全的。 inner
可能会被公开,因为它是不可变的。这样,Map
的丰富接口将可用,但不幸的是,不会创建另一个TypedMap
。
你的意思是你想要的'enemyDetailsStore'返回一个事情,如果'myEnemy'延伸'VerticalMover',还有一件事,如果它延伸'RandomMover'?如果它同时延伸呢? –
是的,这就是我的意思。但我开始怀疑我的整个想法的理智。也许我应该在特征中嵌入一些关键字串并将其用作关键字。因此,在特质线性化的情况下,最后一个压倒性的特性会将EnemyContainer设置为用于显示敌人的纹理。 – vertti
大多数时候,特质/界面的要点是说“我知道怎么做* X *”,同时允许X的不同实现。在没有其他细节的情况下,我会认为最自然的设计会应该让'Moving'特性直接具有某种'getMovingStrategy'或'move'方法,您可以在垂直和随机移动器相减中实现相应的功能。 –