gpt4 book ai didi

Java泛型编译错误

转载 作者:行者123 更新时间:2023-12-02 07:47:32 25 4
gpt4 key购买 nike

我不明白为什么编译器不接受这段代码

import javax.swing.event.EventListenerList;

import java.util.EventListener;


public class GenericEventsManager {

EventListenerList listeners = new EventListenerList();


public <T extends EventListener> void addListener(T listener) {
listeners.add(listener.getClass(), listener);
}
}

我得到的错误是

The method add(Class<T>, T) in the type EventListenerList is not applicable for the arguments (Class<capture#1-of ? extends EventListener>, T)

addListener中的参数是扩展EventListener的类型,因此listener.getClass()返回Class<? extends EventListener> ,这正是 EventListenerList.add 方法所期望的

有人能解释一下吗?我有一种感觉,这与 getClass() 在编译时未解析有关,但对我来说仍然没有意义

最佳答案

Generic parameters without wildcards are not variant and therefore require exactly the same types (not sub-types, not super types). (source)

编译器根本不会让你这样做。正如错误消息所暗示的那样, Class 上的类型参数参数必须与第二个参数的类型完全相同,但在上面的代码中并非如此。

<小时/>

How can they not be identical?

因为返回类型为listener.getClass()Class<? extends EventListener> ,不是Class<T> 。您可以 - 但我不建议这样做 - 转换返回的 Class进行编译:

listeners.add((Class<T>)listener.getClass(), listener);

这样做时您会收到编译器警告:

Type safety: Unchecked cast from Class<capture#1-of ? extends EventListener> to Class<T>

因为这不是(类型)安全的强制转换。

<小时/>

造成这种情况的根本原因可能(老实说我不确定)只是 EventListenerList#add() 声明中糟糕的 API 设计。 。通常PECS is used in this kind of situation ;可能有充分的理由 add()不是通配符。

关于Java泛型编译错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10623219/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com