有没有办法绕过Java无法将generics参数转换为非generics?

在C ++中,我可以像这样编写代码:

class Shader { ... void setUniform(GLuint handle, int value); void setUniform(GLuint handle, float value); void setUniform(GLuint handle, const std::vector &value); ... }; class UniformValueBase { ... GLuint handle; Shader &shader; virtual void apply() = 0; }; template class UniformValue: public UniformValueBase { ... T value; virtual void apply() override { shader.setUniform(handle, value); }; 

T是在Shader有一个setUniform方法的任何types,并且如果我尝试使用一个不受支持的T (这正是我想要的行为),则无法编译。

不幸的是,相当于Java或Kotlin中不起作用,因为generics基于types擦除,意味着UniformValue只用T作为Object / Any来实现一次。

我只需要支持大约六种不同的types,所以使用UniformValueBase非generics子类而不是generics是可行的,但是有没有一个优雅和可扩展的习惯用法呢,要么使用Kotlin不具有Java的特性,要么一个在两种语言的作品?

基本的原因并不是真正的types擦除:这是因为C ++模板在实例化后进行了types检查,Java(和Kotlin以及大多数具有此function的其他语言)都检查通用代码本身。 所以你需要一个约束条件,要求T有一个静态方法,Kotlin和Java都不支持。 我所知道的唯一一种语言是F# ,它在JVM上不可用。 斯卡拉有一个非常好的和一般的解决方法称为typeclass模式,这是不支持在Kotlin。

看起来这是不可能的。 types正在用Java擦除,没有模板。