Как неявно выяснить тип во главе бесформенного HList - PullRequest
0 голосов
/ 10 июля 2019

Допустим, у меня есть следующее:

case class TestField(value: String)
case class TestField2(value: String)

implicit class ProductExtensions[T <: Product](val value T) extends AnyVal {

  def mapTo[R <: Product](implicit tGen: Generic.Aux[T, String :: HNil], rGen: Generic.Aux[R, String :: HNil]: R = ???

}

val testField2 = TestField("my value").mapTo[TestField2]
// TestField2("my value")

Могу ли я "увеличить" функцию mapTo для работы с типами, отличными от String, без указания типа?

Примечание TestField, ни TestField2 реализуют AnyVal (и я не хочу их), поэтому я не могу использовать Unwrapped.

Редактировать

@ Dmytro_Mitin ответ работает в моем примере выше, но если я добавлю пример к этому:

implicit class ProductExtensions[T <: Product](val value T) extends AnyVal {

  def mapTo[R <: Product](implicit tGen: Generic.Aux[T, String :: HNil], rGen: Generic.Aux[R, String :: HNil], o: OtherImplicit[String]): R = ???

}

... так что я как бы ищу это на работу (но это не так):

implicit class ProductExtensions[T <: Product, U](val value T) extends AnyVal {

  def mapTo[R <: Product](implicit tGen: Generic.Aux[T, U :: HNil], rGen: Generic.Aux[R, U :: HNil], o: OtherImplicit[U]): R = ???

}

Есть идеи?

1 Ответ

2 голосов
/ 10 июля 2019

Вот обобщенная версия

implicit class ProductExtensions[T <: Product, L <: HList](val value: T) extends AnyVal {
  def mapTo[R <: Product](implicit tGen: Generic.Aux[T, L], rGen: Generic.Aux[R, L]): R = rGen.from(tGen.to(value))
}

Тип астронавта по бесформенному руководству.6.3 Изучение конкретного случая: миграция класса случая https://books.underscore.io/shapeless-guide/shapeless-guide.html#sec:ops:migration


Новая версия

import shapeless.ops.hlist.IsHCons

implicit class ProductExtensions[T <: Product, L <: HList, U, L1 <: HList](val value: T) extends AnyVal {
  def mapTo[R <: Product](implicit 
                          tGen: Generic.Aux[T, L], 
                          rGen: Generic.Aux[R, L], 
                          isHCons: IsHCons.Aux[L, U, L1], 
                          o: OtherImplicit[U]
                         ): R = rGen.from(tGen.to(value))
}

4.3 Зависимые от цепочки функции https://books.underscore.io/shapeless-guide/shapeless-guide.html#sec:type-level-programming:chaining

Scala shapeless Generic.Неявный вспомогательный параметр не найден в неприменяемом

...