我有一个抽象类,如下所示:

abstract class Handler<T> {

    Handler(Class<T> clazz) {
        // ...
    }

    abstract void handle(T object);

}

我正在try 扩展它,其中T是带有通配符泛型参数的类型(出于示例的目的,假设为List<?>).我希望能够做的事情是:

class MyHandler extends Handler<List<?>> {
    MyHandler() {
        super(List.class); 
     // ^ Compiler error: The constructor Handler<List<?>>(Class<List>) is undefined
     // super(List<?>.class); is also a compiler error
    }

    void handle(List<?> object) {
        // ...
    }
}

据我所知,上面的代码是完全安全的,所以我不确定为什么编译器不允许它.我目前的解决方案涉及使用原始类型、不安全的强制转换和隐藏警告,似乎不能成为语言让我使用的解决方案:

class MyHandler extends Handler<List> { // Warning: List is a raw type
    MyHandler() {
        super(List.class); 
    }

    void handle(List objectRaw) { // Warning: List is a raw type
        List<?> object = (List<?>) objectRaw;
        // ...
    }
}

这需要是一个单例,所以我不能将泛型参数添加到MyHandler.如何避免所有这些糟糕的做法(原始类型和强制转换)?这没有理由不安全,我很难相信在Java中没有办法做到这一点.

推荐答案

您可以通过将类对象强制转换为MyHandler构造函数中的类型Class<List<?>>来解决该问题:

MyHandler() {
    super((Class<List<?>>) (Object) List.class); 
}

问题

问题是,在Java中没有简单的方法来表示Class<List<?>>类型的类文字.List.class的类型是Class<List>.

我认为在某些情况下,从第二个类型到第一个类型是不安全的,但在您的代码中可能根本没有问题.

例如,如果您的代码使用clazz来判断使用isAssignableFrom的对象的运行时类型,则可能会遇到麻烦.

类型令牌

如果您使用某种类型标记实现而不是java.lang.Class,例如在Guava中的实现,您将能够表达完全正确的类型的文字:

abstract class Handler<T> {
    Handler(TypeToken<T> clazz) {
        // ...
    }

    abstract void handle(T object);
}

class MyHandler extends Handler<List<?>> {
    MyHandler() {
        super(new TypeToken<List<?>>() {}); 
    }

    void handle(List<?> object) {
        // ...
    }
}

Java相关问答推荐

OpenJDK、4K显示和文本质量

Mat. n_Delete()和Mat. n_release的区别

为什么Java的代码工作(if condition内部的实例)

我需要生成一个文件来整合每个特性执行的所有JSON结果

放气总是压缩整个街区吗?

按属性值从流中筛选出重复项

@Rollback @ Transmission在验收测试中不工作

Javadoc在方法摘要中省略方法

基于接口的投影、原生查询和枚举

当构造函数创建一个新实例时,Java为什么需要&new";

try 在两个不同数组的数字之间求平均值

从Spring6中的JPMS模块读取类时出现问题

使IntelliJ在导入时优先 Select 一个类或将另一个标记为错误

在不使用instanceof或强制转换的情况下从父类变量调用子类方法

在线程Java中调用Interrupt()之后调用Join()

用于Java的Visual Studio代码完成不起作用

Win32函数的JNA绑定DwmGetColorizationColor返回E_INVALIDARG错误

org.springframework.web.HttpRequestMethodNotSupportedException:请求方法';帖子';不支持

关于正则表达式的一个特定问题,该问题与固定宽度负向后看有关

Xml Reader 将 BMP 外部的字符解析为代理项对,这会导致无效的 xml