2013-05-29 3 views
4

Пожалуйста, рассмотрим следующий фрагмент кода (он демонстрирует упрощенную версию моей актуальной проблемы):Scala: Высшее kinded типа в качестве параметра типа

trait Id[Type[_]] { 
    def id[S]: S => Type[S] 
} 

trait IdTransformer[Type[_]] { 
    type Result[_] // depends of Type 
    def idTransform[P]: P => Result[P] 
    def composeWith[Other[_]](other: Id[Other]) = new Id[Result[Other]] { def id[S] = x => idTransform(other.id(x)) } 
} 

// instance example 
class OptionIdTransformer extends IdTransformer[Option] { 
    type Result = Option[_] 
    def idTransform[S] = x => Some(x) 
} 

Там у меня есть Id черта определяет функцию, которая оборачивает значение в тип и признак IdTransformer определяет способ добавления новой логики в операции id. Я хочу, чтобы использовать их в пути, как

Transformer1.composeWith(Transformer2.composeWith(...(idInstance))) 

Но когда я скомпилировать код, я получаю сообщение об ошибке

type Other takes type parameters 

и

IdTransformer.this.Result[<error>] takes no type parameters, expected: one 

в методе composeWith, хотя результат [Other] должен быть более высокого типа и должен принимать один параметр типа.

Пожалуйста, объясните, в чем причина ошибок и существует ли обходное решение.

ответ

1

Вы пытаетесь создать более сортный тип с двумя другими типами более хегерных типов. Для этого нужен трюк type lambda.

trait IdTransformer[Type[_]] { 
    type Result[_] // depends of Type 
    def idTransform[P]: P => Result[P] 
    def composeWith[Other[_]](other: Id[Other]) = new Id[({type λ[α] = Result[Other[α]]})#λ] { def id[S] = x => idTransform(other.id(x)) } 
} 
Смежные вопросы