我的应用程序有一个简单的插件API。它包装在插件开发人员可以使用的单独的JAR中。核心应用程序实现API中包含的接口,并将其公开给ServiceLoader
加载的插件。
考虑以下代码:
public interface ILayer {}
public class Layer implements ILayer {
public void internalMethod() { /*snip*/ }
}
public interface IPlotter {
List<ILayer> getLayers();
}
public class Plotter implements IPlotter {
private ObservableList<Layer> layers = FXCollections.observableArrayList();
@Override
public ObservableList<Layer> getLayers() { // incompatible returned type
return layers;
}
}
我的要求是:
在内部,
ObservableList
个中的Layer
个可用API仅公开
List
个ILayer
个不幸的是,将
ObservableList<Layer>
强制转换为List<ILayer>
是非法的。在API中返回
List<Layer>
会暴露internalMethod()
的Layer
,所以这不好。我也可以有
private ObservableList<ILayer> layers
,然后将Layer
实际存储在其中,但这每次我使用internalMethod()
时都需要转换其项,而我对此想法并不热心。有没有解决此问题的解决方案?
最佳答案
一种选择是更改接口方法的签名,以允许返回ILayer的子类型:
interface IPlotter {
List<? extends ILayer> getLayers();
}
class Plotter implements IPlotter {
private ObservableList<Layer> layers = FXCollections.observableArrayList();
@Override
public List<? extends ILayer> getLayers() {
return layers;
}
}
主要缺点是调用
List<? extends ILayer> layers = plotter.getLayers();
的人将无法添加到列表中:layers.add(someLayer);
无法编译。这可能是也可能不是问题。关于java - 干净的解决方案,将“ObservableList <Foo>”转换到“List <IFoo>”?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/34045925/