Во-первых, вы должны указать типом надписи, что None
имеет тип Option[...]
(вот почему в Cats есть none[...]
и .some
, см. также , элемент 9).
Во-вторых, вы должны использовать маппер с типом возврата вместо стандартного shapeless.ops.hlist.Mapper
trait MapperWithReturnType[HF, Out <: HList] extends Serializable {
type In <: HList
def apply(t: In): Out
}
object MapperWithReturnType {
type Aux[HF, Out <: HList, In0 <: HList] =
MapperWithReturnType[HF, Out] { type In = In0 }
def instance[HF, Out <: HList, In0 <: HList](f: In0 => Out): Aux[HF, Out, In0] =
new MapperWithReturnType[HF, Out] {
override type In = In0
override def apply(t: In0): Out = f(t)
}
implicit def hnilMapper[HF <: Poly]: Aux[HF, HNil, HNil] = instance(_ => HNil)
implicit def hconsMapper[HF <: Poly, InH, InT <: HList, OutH, OutT <: HList](implicit
hc : poly.Case1.Aux[HF, InH, OutH],
mt : Aux[HF, OutT, InT]
): Aux[HF, OutH :: OutT, InH :: InT] = instance(l => hc(l.head) :: mt(l.tail))
}
implicit final class HListOps[L <: HList](l : L) extends Serializable {
def mapWithReturnType[Out <: HList](f: Poly)(implicit
mapper: MapperWithReturnType.Aux[f.type, Out, L]
): Out = mapper(l)
}
val x = ((None: Option[Int]) :: (None: Option[Int]) :: 12 :: HNil)
.mapWithReturnType[BestBeforeDate](PolyToField)
x: BestBeforeDate