我目前正在审查对 Android 应用程序的更改,将应用程序升级为使用 Java 8。
在审查过程中,我注意到以下代码被加下划线表示为错误:
List<MappableTask> tasks = Observable.fromIterable(taskMapHoldingPresenter.getMappableTasks())
.filter(isMappableTask)
.toList()
.blockingGet();
现在显示以下内容:
Incompatible Types.
Required: List<MappableTask>
Found: List<capture<? extends MappableTask>>
getMappableTasks()
方法在接口(interface)中定义如下:
List<? extends MappableTask> getMappableTasks();
请注意 MappableTask
是各种模型类实现的接口(interface)。
List<MappableTask> list = taskMapHoldingPresenter.getMappableTasks();
是怎么回事?无效?
此代码按预期构建。如前所述,在将应用程序升级为使用 Java 8 之前未显示此错误。为什么会出现此问题?
最佳答案
您的接口(interface)声明允许 getMappableTasks
返回任何 MappableTask
列表的方法子类。假设 MappableAsyncTask
延伸MappableTask
你的界面理论上可以返回List<MappableAsyncTask>
.
class MappableAsyncTask extends MappableTask {
}
class AsyncPresenter implements TaskMapHoldingPresenter {
@Override
public List<? extends MappableTask> getMappableTasks() {
List<MappableAsyncTask> result = new ArrayList<>();
result.add(new MappableAsyncTask());
return result;
}
}
但是List<MappableAsyncTask>
不是 List<MappableTask>
的子类, 所以你不能分配 getMappableTasks
结果为 tasks
变量。
List<MappableTask> tasks = asyncPresenter.getMappableTasks(); // wrong
此限制的存在是有原因的。如果可以进行此分配,您可以轻松添加 MappableTask
实例到 tasks
列表,打破实际列表执行契约(Contract)。请记住 getMappableTasks
返回的实际列表方法只能包含 MappableAsyncTask
的实例.
List<MappableTask> tasks = asyncPresenter.getMappableTasks(); // wrong
tasks.add(new MappableTask()); // wrong
更多信息 here .
关于java - 不兼容的类型,发现 List<capture<?仅在 Java 8 中扩展模型>>,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48177208/