gpt4 book ai didi

scala - 使用 shapeless Mapper 无需指定结果类型

转载 作者:行者123 更新时间:2023-12-04 17:24:20 24 4
gpt4 key购买 nike

对于习惯于 Scala 类型级编程的开发人员来说,这似乎是一个经典问题,但我找不到(或者我不知道如何搜索)解决方案或模式。假设我有一个这样的类:

abstract class TypedTest[Args <: HList](implicit val optMapper: Mapped[Args, Option]) {
type OptArgs = optMapper.Out

def options: OptArgs // to be implemented by subclasses
}

我希望此类的用户使用 HList 实例化它类型参数( Args ),该类提供了一种方法来检索 HList实例在 Option 中包含每个指定类型的实例( OptArgs )。我正在使用无形 Mapped为此键入类。请注意,我没有 Args 的实例在实例化时提供。

此代码不起作用,因为编译器不会推断 OptArgs 的具体类型甚至是明显正确的实现,例如 def options = HNil产生编译错误。使用 Aux 模式的相同代码:
abstract class TypedTest[Args <: HList, OptArgs <: HList](implicit val optMapper: Mapped.Aux[Args, Option, OptArgs]) {
def options: OptArgs
}

这迫使我在实例化时指定两个列表,这使得外部 API 变得不必要地冗长。有解决方法吗?

最佳答案

这是我的理解,但我不是 100% 确定并且很乐意接受纠正。

类型成员(member)TypedTest.OptArgs不是抽象类型而是类型别名。 TypedTest 的所有子类都是相同的类型– Mapped[Args, Option].Out 的别名,它是一个抽象类型,不能与除自身以外的任何类型统一。创建子类时,类型成员 OptArgs没有被覆盖。

使用 Mapped.Aux 时更清楚具有 Out0 的存在类型,这或多或少相当于上面的 IIUC:

abstract class TypedTest[Args <: HList](
implicit val optMapper: Mapped.Aux[Args, Option, T] forSome { type T }) {

type OptArgs = optMapper.Out

def options: OptArgs // to be implemented by subclasses
}

val intTest = new TypedTest[Int :: HNil] {
def options = Some(1) :: HNil
}

Error:(18, 29) type mismatch;
found : shapeless.::[Some[Int],shapeless.HNil]
required: this.OptArgs
(which expands to) T
def options = Some(1) :: HNil

不幸的是,我不知道任何可能的解决方案,除了添加 Out作为类型参数或定义 OptArgs作为抽象类型并在每个子类中明确指定它。

关于scala - 使用 shapeless Mapper 无需指定结果类型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38882347/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com