gpt4 book ai didi

java - 对 Netty 在 GenericFutureListener 中使用的泛型类型感到困惑?

转载 作者:行者123 更新时间:2023-11-29 08:30:50 28 4
gpt4 key购买 nike

在netty中定义监听器如下:例如在 io.netty.util.concurrent.CompleteFuture 类中:

@Override
public Future<V> addListener(GenericFutureListener<? extends Future<? super V>> listener) {
if (listener == null) {
throw new NullPointerException("listener");
}
DefaultPromise.notifyListener(executor(), this, listener);
return this;
}

据我所知: future 表示一个 Class 的集合,它取代了 V。所以它是继承树中的一个集合,因为我们至少有 Future 和 Future 。假设集合的名称是 C。

那么问题来了,什么是? extends C 意味着 C 是一个集合?

希望有人能赐教!

最佳答案

我假设你上面的声明来自 Netty 的 Promise类(class)。我认为无论如何我的回答都应该有效,因为你的问题似乎是关于协变和逆变,而不是明确地关于 Netty 的 API。

public interface Promise<V> extends Future<V> {

Promise<V> addListener(GenericFutureListener<? extends Future<? super V>> listener);
//...
}

此处泛型的目的是使 API 对其用户更具可塑性。

假设您有三个不同的 GenericFutureListener三个不同类型参数的对象:Integer , NumberObject .

GenericFutureListener<Future<Integer>> fl1 = System.out::println;
GenericFutureListener<Future<Number>> fl2 = System.out::println;
GenericFutureListener<Future<Object>> fl3 = System.out::println;

注意 IntegerNumber 的子类型这又是 Object 的子类型.

假设现在我们有一个 Promise类型 Integer , 大致如下

Promise<Integer> p = somePromise;

我们的方法声明将被编译器解释为

Promise<Integer> addListener(GenericFutureListener<? extendsFuture<? super Integer>> listener);

这基本上是说 GenericFutureListener可能对 Integer 类型的 future 进行操作、或其任何父类(super class)型

这显然使 API 更加灵活,例如,我可以添加我之前定义的任何监听器,以便在我对 Integer 的 promise 得到解决时收到通知:

p.addListener(fl1);
p.addListener(fl2);
p.addListener(fl3);

请注意,我并没有被迫为明确类型 Integer 的 future 提供监听器。 .如果您考虑一下,那完全有道理,因为如果我的 promise p产生 Integer , 和一个 Integer 是一个 Number ,然后是一个知道如何处理 Number future 的听众应该能够处理 Integer 的 future 以及。如果我的听众知道如何处理 Object 的 future , 和一个 Integer 是一个 Object , 那么让 future 的听众应该没有问题 Object处理 Integer 的 future ,对吧?

嗯,这正是Future<? super V>在上面的声明中表示。这是称为逆变的概念。

现在,事实是在 Netty 中 Future是一个接口(interface),许多不同的类可以实现 Future .我们想要我们的 GenericFutureListener能够使用 Future 的任何子类型而不仅仅是 Future本身,对吗?

例如,Promise实际上是 Future 的子类型:

GenericFutureListener<Promise<Integer>> fl4 = System.out::println;
GenericFutureListener<Promise<Number>> fl5 = System.out::println;
GenericFutureListener<Promise<Object>> fl6 = System.out::println;

如您所见,GenericFutureListener接受 Promise作为类型参数。这要归功于 <? extends Future> 的声明.没有它,GenericFutureListener只会接受 Future在此处键入,这会使该 API 的灵 active 大大降低,对吧?

这个概念称为协方差,它再次用于使 API 对其用户更加灵活。

现在我们可以实现最初的 promise ,同时添加这些第二组监听器:

p.addListener(fl4);
p.addListener(fl5);
p.addListener(fl6);

就是这样。由于协变和逆变的正确使用,API 更加灵活。

关于java - 对 Netty 在 GenericFutureListener 中使用的泛型类型感到困惑?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48378767/

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