【问题标题】:Can someone explain to me what the Shapeless library is for? [closed]有人可以向我解释 Shapeless 库的用途吗? [关闭]
【发布时间】:2014-03-11 10:37:57
【问题描述】:

有人可以简单地向我解释一下 Shapeless 库的用途吗?

Scala 具有泛型和继承功能,所以我有点困惑 Shapeless 的用途。

也许一个用例来澄清事情会有所帮助。

【问题讨论】:

    标签: scala shapeless


    【解决方案1】:

    有点难以解释,因为 shapeless 具有广泛的特征;我可能会发现“用简单的术语解释变量的用途”更容易。你肯定想从feature overview开始。

    广义上讲,shapeless 是关于使用类型进行编程。在编译时做一些通常在运行时做的事情,精确跟踪列表中每个元素的类型,能够从元组转换为 HLists 到案例类,创建多态函数(相对于方法),等等

    典型的使用场景如下:

    • 从某处读取一堆值到List
    • List 的类型安全转换为HList
    • 使用多态函数映射HList,例如标准化值
    • 将第 3 个元素(静态已知为 Int)转换为 0 填充字符串
    • 使用 HList 中的值构造案例类

    作为参考,HList 将具有精确的类型,例如 Int :: String :: Boolean :: HNil(是的,这确实单一类型),其中所有内容都固定下来并且大小固定。因此,您要么需要在编译时确切地知道 HList 中的内容,要么需要类型安全的强制转换。

    如果你获取这样一个 HList 的tail,你会得到一个String :: Boolean :: HNil,并且编译时保证它的头部将是一个String。在头部添加一个值同样会保留所有涉及的类型。

    Shapeless 还带有 Generic 类型类,允许您对元组和案例类使用 HList 操作。

    我倾向于使用的其他功能是:

    • Coproducts,它允许您静态键入一个值,例如“StringDoubleInt,但仅此而已”(很像 Either,但不仅限于两种可能性)

    • Lenses,简化了嵌套案例类的使用。

    【讨论】:

      【解决方案2】:

      在您尝试使用类型并委托或打开类型之前,查看HList 可能看起来令人费解。看看以下内容:

      val myList = 1 :: 2 :: "3" :: fred :: Nil
      

      这里的myList 是什么类型?如果您要检查它,您会发现它的类型为List[Any]。这不是很有帮助。如果我尝试在它上面使用以下PartialFunction[Any]map,则更有帮助:

      myList.map{
        case x: Int => x
        case x: String => Int.parseInt(x)
      }
      

      在运行时,这可能会抛出MatchError,因为我实际上并没有告诉你fred 是什么类型。它可以是Fred 类型。

      使用HList,您可以在编译时知道您是否未能捕获该列表的其中一种类型。在上面,如果我在访问第三个元素时定义了myList = 1 :: 2 :: "3" :: fred :: HNil,它的类型将是String,这将在编译时知道。

      正如@KevinWright 所说,除了Shapeless 之外,它还有更多功能,但HList 是该库的定义功能之一。

      【讨论】:

        【解决方案3】:

        Shapeless 中的一切都有两个共同点:

        首先,它不在 Scala 标准库中,但可以说应该在。因此,询问 Shapeless 的用途有点像询问 Scala 标准库的用途!它适用于一切。这是一个手提包。

        (但它不是一个完全随意的抓包,因为:)

        其次,Shapeless 中的所有内容都在编译时提供了增强的检查和安全性。 Shapeless 中没有任何东西(我能想到的?)实际上在运行时“做”任何事情。当你的代码被编译时,所有有趣的动作都会发生。目标始终是增加信心,即如果您的代码完全编译,它不会在运行时崩溃或做错事。 (因此这个值得注意的俏皮话:https://twitter.com/mergeconflict/status/304090286659866624

        https://stackoverflow.com/a/4443972/86485 上有一个很好的关于类型级编程的介绍以及更多资源的链接。

        【讨论】:

        • “首先,它不在 Scala 标准库中,但可以说应该在。”如果发生这种情况,我会逃跑......然后尖叫。
        • @JayZee 你为什么这么说?
        • 让我来比较一下……如果 scala 类型安全是素食主义,无形就是素食主义!它增加了额外的类型安全层,在我看来,这使 scalac 编译器已经复杂的生活变得复杂。 Shapeless 需要更多的隐式和更多的类型类。我不是 scala 编译的超级专家,但你为 shapeless 付出的代价是编译器在使用 shapeless 时会遇到困难(至少是我的经验)并且会变慢。我更喜欢有一堆 "isInstanceOf" ,有时会碰到 ClassCastException 并修复而不是依赖于无形下的魔法。
        • 还要考虑到,即使您的 IDE 也很难输入推断内容或尝试编译您的代码,即使这对您来说可能不是问题。
        • 强调“可以说”。
        猜你喜欢
        • 1970-01-01
        • 2011-01-08
        • 1970-01-01
        • 2016-08-22
        • 2020-08-16
        • 2021-02-18
        • 2011-05-08
        • 2014-03-16
        相关资源
        最近更新 更多