I have a class hierarchy of Items that each need a corresponding ItemTemplate instance as a constructor parameter. I’d like to write a generic function to instantiate any Item subclass by giving it Item and ItemTemplate as type parameters, using it like this:
val newItem = instantiateItem[ItemClass, TemplateClass](templateInstance)
After a bit of research I now have
def instantiateItem[I, T](implicit mf: Manifest[I], template: T): I = {
val constructor = mf.erasure.getConstructor(classOf[T])
constructor.newInstance(template).asInstanceOf[I]
}
But this doesn’t compile, the classOf[T] gives the error
Class type required but T found
I tried replacing classOf[T] with classManifest[CM].erasure but this doesn’t work as CM needs to be context bounded to ClassManifest, and apparently it’s not possible to use bounded type parameters with implicit parameters.
Is it possible to do what I want here?
You can get the
templateclass simply by callingtemplate.getClass. It requirestemplateto be a subtype ofAnyRef, so either you cast it toAnyRef(forcing boxing of primitive types) or you add an upper bound forT:If you want to pass in
templateexplicitly, as indicated by the code in your question, you need to separate implicit and explicit arguments, e.g.aka
In general if possible you could avoid having to use reflection at all with careful design: