Можно ли принять произвольный экстрактор в качестве аргумента метода
Я хотел бы повторно использовать существующие экстракторы и составить их. A => Option[B]
идеально сочетается с B => Option[C]
,
Но я запутался, как я мог выразить такое отношение в коде.
Очевидный способ не доступен по уважительной причине:
type Extractor[F,T] = {
def unapply(from : F) : Option[T]
}
def bind[A,B,C](l : Extractor[A,B], r : Extractor[B,C]) = new {
def unapply(from : A) : Option[C] = l.unapply(from).flatMap(r.unapply _)
}
скалярный ответ:
Extractors.scala:7: error: Parameter type in structural refinement may not refer to an abstract type defined outside that refinement
def unapply(from : A) : Option[C] = l.unapply(from).flatMap(r.unapply _)
^
Extractors.scala:3: error: Parameter type in structural refinement may not refer to an abstract type defined outside that refinement
def unapply(from : F) : Option[T]
^
two errors found
Интернет говорит, что это ожидаемое поведение из-за стирания типа.
Можно ли перефразировать код, чтобы он работал правильно?
1 ответ
Тип параметра в структурном уточнении может не относиться к абстрактному типу, определенному вне этого уточнения`
Как ошибка вызвать, для structure type
не могу отослать generic type
что определено снаружи.
Для вашего примера вы можете использовать trait
сделать то же самое, например:
trait Extractor[F, T] {
def unapply(from: F): Option[T]
}
def bind[A, B, C](l: Extractor[A, B], r: Extractor[B, C]) = new Extractor[A, C] {
override def unapply(from: A): Option[C] = l.unapply(from).flatMap(r.unapply)
}