Path dependent type
Abstract type member
Scalaでは、abstract type memberとtype projectionを使ってtype family を作ることができる。
object PathDepType { trait K { type A // abstract type member } trait a extends K { override type A = Int } trait b extends K { override type A = Char } implicitly[Int =:= a#A] implicitly[Char =:= b#A]
Path
Pathとは、大雑把に言うとvalueのidentifier、あるいはそれらを.
で繋げたものである。
Method呼び出しが混ざっていてはいけない。
Pathのequality=
は、Any.==
は使用されず、以下から帰納的に決められる(と思う)。
x = x
y: x.type
ならば、x = y
Singleton type member
Scalaは組み込みのsingleton type familyとしてtype
というtype memberを提供しているが、引数がpathに制限されている。
つまり、
とすると、
Path dependent type family
Type family から次のようなdependent type familyを作れる:
これをpath dependent type family over と(でも)言う。 その適用結果をpath dependent typeという。
特に の場合は
を使うことが出来る。
object c extends K { override type A = String } implicitly[c.A =:= c.type#A] implicitly[c.A =:= String]
Path dependent method
Return typeがpath dependent typeになっているmethodのことをpath dependent methodという(ことにする)。つまり、path dependent type familyのproductのこと。
def id(x: AnyRef): x.type = x val s: String = id("hello") }
機能的にはpolymorphic methodのようになっている。 実践的にはfunctional dependencyを実装するとき必要になると思われる。
参考文献
*1:今のところなんらかの理由でAnyRefのsubtypeでなくてはいけない