Scala 如何在运行时获得适当的typeclass实例?

Scala 如何在运行时获得适当的typeclass实例?,scala,typeclass,shapeless,Scala,Typeclass,Shapeless,第一部分 假设我有一个类型类trait Show[T]{def print(T:T):String},其中包含String和Int的实例。假设我有一个值,其特定类型仅在运行时已知: val x: Any = ... 如何获取适当的typeclass实例(在运行时,因为我们静态地不知道类型),并对其进行处理 请注意,定义一个只给出typeclass实例的方法是不够的: def instance(x: Any): Show[_] 由于Show.print需要静态已知的参数类型T,我们仍然无法对实

第一部分

假设我有一个类型类
trait Show[T]{def print(T:T):String}
,其中包含
String
Int
的实例。假设我有一个值,其特定类型仅在运行时已知:

val x: Any = ...
如何获取适当的typeclass实例(在运行时,因为我们静态地不知道类型),并对其进行处理

请注意,定义一个只给出typeclass实例的方法是不够的:

def instance(x: Any): Show[_]
由于
Show.print
需要静态已知的参数类型
T
,我们仍然无法对
实例的结果执行任何操作。因此,实际上,我们需要能够动态地分派到使用实例的已定义函数,例如:

def display[T](t: T)(implicit show: Show[T]) = "show: " + show.print(t) + "\n"
因此,假设定义了
display
,我们如何调用
display
,传递一个适当的
Show
实例。即正确调用
显示(x)
的东西

Miles Sabin在这里使用运行时编译(Scala eval)实现了这一点,作为“登台”的一个示例,但只使用了关于发生了什么的备用文档:

迈尔斯的方法能放进图书馆吗?此外,这种方法的局限性是什么,例如对于
Seq[T]
之类的泛型类型

第二部分

现在假设
T
由一个密封类型限定(这样就可以枚举所有子类型):


trait Show[T对于第二部分,我认为只定义一个模式在类层次结构的所有叶上都匹配的函数比定义一个typeclass更有意义。我认为那没关系,这或多或少就是我现在代码中的内容。但我碰巧不止一次在代码中有这个模式,所以模式匹配开始感觉像把样板交给我。把印刷品在我的实际情况下,单独对象中的实现似乎更具模块性。此外,如果这可以推广,它似乎是一个功能强大的工具。FWIW我的实际情况是:我有一个带有子命令的CLI程序。每个子命令都有自己的case类。我使用typeclass来执行每个命令:@tksfz是否有任何通用的非模式匹配解决方案的进展?不,我没有听说过任何解决方案
trait Show[T <: Foo]
sealed trait Foo
case class Alpha(..) extends Foo
case class Beta(..) extends Foo