简体   繁体   English

如何从 Scala TypeTag 获取通用的简单类名?

[英]How to get generic simple class name from scala TypeTag?

How can I get the simple class name including generic using TypeTag ?如何使用TypeTag获取包括泛型在内的简单类名? I think that the method signature should be like:我认为方法签名应该是这样的:

def getClassName[A: TypeTag](a: A): String

getClassName(Map("a" -> 123)) should return Map[String,Int] . getClassName(Map("a" -> 123))应该返回Map[String,Int]


Things I've tried:我尝试过的事情:

def getClassName[A: TypeTag](a: A): String = {
  typeOf[A].typeSymbol.name.toString
}

scala> getClassName(Map("a" -> 123))
res1: String = Map
def getClassName[A: TypeTag](a: A): String = {
  typeOf[A].typeSymbol.toString
}

scala> getClassName(Map("a" -> 123))
res1: String = trait Map
def getClassName[A: TypeTag](a: A): String = {
  typeOf[A].toString
}

scala> getClassName(Map("a" -> 123))
res1: String = scala.collection.immutable.Map[String,Int] // It knows the full type!
def getClassName[A: TypeTag](a: A): String = {
  typeOf[A].typeSymbol.fullName
}

scala> getClassName(Map("a" -> 123))
res1: String = scala.collection.immutable.Map

From here: https://docs.scala-lang.org/overviews/reflection/typetags-manifests.html从这里: https : //docs.scala-lang.org/overviews/reflection/typetags-manifests.html

import scala.reflect.runtime.universe._

def getClassName[T](x: T)(implicit tag: TypeTag[T]): String = {
    tag.tpe match { case TypeRef(_, t, args) => s"""${t.name} [${args.mkString(",")}]""" }
}

getClassName(Map("a" -> 123))

res5: String = Map [java.lang.String,Int]

UPDATE: Shorter version with full class names更新:具有完整类名的较短版本

 def getClassName[T: TypeTag](x: T) = typeOf[T].toString

getClassName(Map("a" -> 123))
res1: String = scala.collection.immutable.Map[java.lang.String,Int]

I'll add my answers to this based on Artem Aliev's answer , since it doesn't seems like Scala has this built-in.我将根据Artem Aliev 的答案添加我的答案,因为 Scala 似乎没有内置这个。 This method uses context bound syntax instead of an implicit parameter.此方法使用上下文绑定语法而不是隐式参数。

def getClassName[A: TypeTag](a: A): String = {
  val typeArgs = typeOf[A].typeArgs
  s"${typeOf[A].typeSymbol.name}${if (typeArgs.nonEmpty) typeArgs.mkString("[",",", "]") else ""}"
}
scala> getClassName(Map("a" -> 123))
res1: String = Map[String,Int]

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM