Il modo più conveniente per fare questo genere di cose è di solito scrivere la propria classe di tipo. Ecco un rapido schizzo di lavoro:
import shapeless._
trait T[I, O] extends (I => O)
trait Pipeline[P <: HList] {
type In
type Out
type Values <: HList
}
object Pipeline {
type Aux[P <: HList, In0, Out0, Values0 <: HList] = Pipeline[P] {
type In = In0; type Out = Out0; type Values = Values0
}
def apply[P <: HList](
implicit pipeline: Pipeline[P]
): Aux[P, pipeline.In, pipeline.Out, pipeline.Values] = pipeline
implicit def onePipeline[I, O]: Aux[T[I, O] :: HNil, I, O, I :: O :: HNil] =
new Pipeline[T[I, O] :: HNil] {
type In = I
type Out = O
type Values = I :: O :: HNil
}
implicit def longerPipeline[I, O, P <: HList, Out0, Values0 <: HList](
implicit pipeline: Aux[P, O, Out0, Values0]
): Aux[T[I, O] :: P, I, Out0, I :: Values0] =
new Pipeline[T[I, O] :: P] {
type In = I
type Out = Out0
type Values = I :: Values0
}
}
E poi (riformattato per chiarezza):
scala> Pipeline[T[String, Int] :: T[Int, Char] :: HNil]
res5: Pipeline[T[String, Int] :: T[Int, Char] :: HNil] {
type In = String
type Out = Char
type Values = String :: Int :: Char :: HNil
} = [email protected]
scala> Pipeline[T[String, Int] :: T[Char, Char] :: HNil]
<console>:19: error: could not find implicit value for parameter
pipeline: Pipeline[[T[String, Int] :: T[Char, Char] :: HNil]
Pipeline[T[String, Int] :: T[Char, Char] :: HNil]
^
Il gasdotto non valida non si compila, e per la valida otteniamo gli endpoint ei valori intermedi correttamente dedotto .
Solo pensando ad alta voce, ma forse dovresti modellare i tubi in modo esplicito e non solo i passaggi di elaborazione. Perché i tubi hanno lo stesso tipo a "fine" ... –
Ereditarietà? Tutte le tue classi P1, P2, ... PN potrebbero ereditare dalla stessa super classe in modo da utilizzare T [PSUPER, PSUPER] –
@rspencer, presumo che l'OP voglia sapere che il secondo parametro tipo del tipo di uno l'elemento list è dello stesso tipo del primo parametro type del tipo dell'elemento successivo della lista. Non solo che sono tutti T [Px, Py] per alcuni xey. –