ClassTag (Scala) 上的类型不匹配运行时错误
Type mismatch runtime error on ClassTag (Scala)
我是一名 C++ 程序员,正在努力学习 Scala。我想使用 C++ template
实现类似于以下代码的东西
template<typename T>
class Foo {
public:
T* bar;
/////////////////Other Code Omitted//////////////////////////
};
由于类型擦除,它在 Scala 中的对应部分将无法编译
class Foo[E](){
val bar = new E() //Will not compile
}
我整晚都在寻找解决方法,这似乎是其中之一
package test
import scala.reflect._
object Type {
def newInstance[T: ClassTag](init_args: AnyRef*): T = {
classTag[T].runtimeClass.getConstructors.head.newInstance(init_args: _*).asInstanceOf[T]
}
}
class Foo[T1:ClassTag](init_args: AnyRef*){
val bar = Type.newInstance[T1](init_args)
}
class TestClass(val arg:String){
val data = arg
}
但是,当我尝试在 Scala 控制台中实例化一个 (val test = new Foo[Test]("test")
) 时,出现以下错误
java.lang.IllegalArgumentException: argument type mismatch
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
at ParActor.Type$.newInstance(ParActor.scala:32)
at ParActor.Foo.<init>(ParActor.scala:37)
... 35 elided
我不确定是什么原因导致了这个问题以及如何解决这个问题。也欢迎其他解决方法。
你应该转
Type.newInstance[T1](init_args)
进入
Type.newInstance[T1](init_args: _*)
: _*
所做的是将列表或序列转换为可变参数。可变参数 AnyRef*
实际上是 IndexedSeq[AnyRef]
,更具体地说是 WrappedArray[AnyRef]
。因此,当您将 init_args
作为参数传递给 newInstance
而没有告诉编译器将其解释为可变参数参数时,您实际上是在传递 WrappedArray(WrappedArray("test"))
.
我是一名 C++ 程序员,正在努力学习 Scala。我想使用 C++ template
实现类似于以下代码的东西template<typename T>
class Foo {
public:
T* bar;
/////////////////Other Code Omitted//////////////////////////
};
由于类型擦除,它在 Scala 中的对应部分将无法编译
class Foo[E](){
val bar = new E() //Will not compile
}
我整晚都在寻找解决方法,这似乎是其中之一
package test
import scala.reflect._
object Type {
def newInstance[T: ClassTag](init_args: AnyRef*): T = {
classTag[T].runtimeClass.getConstructors.head.newInstance(init_args: _*).asInstanceOf[T]
}
}
class Foo[T1:ClassTag](init_args: AnyRef*){
val bar = Type.newInstance[T1](init_args)
}
class TestClass(val arg:String){
val data = arg
}
但是,当我尝试在 Scala 控制台中实例化一个 (val test = new Foo[Test]("test")
) 时,出现以下错误
java.lang.IllegalArgumentException: argument type mismatch
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
at ParActor.Type$.newInstance(ParActor.scala:32)
at ParActor.Foo.<init>(ParActor.scala:37)
... 35 elided
我不确定是什么原因导致了这个问题以及如何解决这个问题。也欢迎其他解决方法。
你应该转
Type.newInstance[T1](init_args)
进入
Type.newInstance[T1](init_args: _*)
: _*
所做的是将列表或序列转换为可变参数。可变参数 AnyRef*
实际上是 IndexedSeq[AnyRef]
,更具体地说是 WrappedArray[AnyRef]
。因此,当您将 init_args
作为参数传递给 newInstance
而没有告诉编译器将其解释为可变参数参数时,您实际上是在传递 WrappedArray(WrappedArray("test"))
.