Created
August 31, 2012 14:31
-
-
Save rabitarochan/3553602 to your computer and use it in GitHub Desktop.
ScalaのClassManifestについてハマった
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// コンストラクタをプライベートにし、コンパニオンオブジェクト経由でのみ生成させる。 | |
class ClassName[A] private (val clazz: Class[A]) { | |
// toString で、引数に指定されたクラスの名称を返す。 | |
override def toString(): String = { | |
clazz.getName | |
} | |
} | |
object ClassName { | |
// Classを直接渡して生成する。 | |
def create[A](clazz: Class[A]): ClassName[A] = new ClassName(clazz) | |
// 型パラメータの情報を ClassManifest から取得して生成する。 | |
def create[A]()(implicit m: ClassManifest[A]): ClassName[A] = new ClassName(m.erasure) | |
// ↑↑コンパイルエラー | |
// /Users/rabitarochan/workspace/classmanifest.scala:10: error: type mismatch; | |
// found : java.lang.Class[_$1] where type _$1 | |
// required: Class[A] | |
// def create[A]()(implicit m: ClassManifest[A]): ClassName[A] = new ClassName(m.erasure) | |
} | |
object Main extends App { | |
val c1 = ClassName.create(classOf[String]) | |
val n1 = println(c1.toString) // => java.lang.String | |
val c2 = ClassName.create[Int] | |
val n2 = println(c2.toString) // => int | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
とりあえずの修正版
https://gist.github.com/3554585
以下説明
ここに
https://github.com/scala/scala/blob/v2.9.2/src/library/scala/reflect/ClassManifest.scala#L26-29
とコメント書いてある通り
trrait ClassManifest[T]
のtraitとしての型パラメーターと、erasure
が返すJClass[_]
の型パラメーターが関連がないつまり
JClass[T]
と定義されていないことが直接の原因。もしそのように定義されていれば、上記のコンパイルエラーは発生しないはず