【发布时间】:2021-04-14 07:03:04
【问题描述】:
我正在尝试将我用 Java 编写的一些代码移植到 Kotlin 中,并且我正在努力解决有关泛型的一些问题。我通常在 Java 中使用工厂模式来返回我想要为给定类型调用的通用接口的实例。
在 Java 中我有这个合同:
public Message<T extends Action> {
private List<T> actions;
..some other properties
}
还有这个界面:
public interface MessageConverter<T extends Action, M extends BaseModel> {
List<M> convertMessage(Message<T> message);
DataType getDataType();
}
最后是这个工厂:
public class MessageConverterFactory {
//This gets populated via DI
private Map<DataType, MessageConverter> converterMap;
public <T extends Action, M extends BaseModel> MessageConverter<T, M> getMessageConverter(DataType dataType) {
return converterMap.get(dataType);
}
}
有了这一切,我就可以做这样的事情了:
Message<T> message = mapper.readValue(messageString, type);
MessageConverter<T, M> messageConverter = messageConverterFactory.getMessageConverter(dataType);
List<M> dataModels = messageConverter.convertMessage(message);
我知道我在一定程度上滥用 Java 中的原始泛型类型来实现这一点,但我认为仍有一些方法可以实现这样的泛型工厂模式。
但是,无论我尝试使用通用方差、星形投影等,我都无法让 Kotlin 接受此代码的任何版本。我得到的最接近的是调用通用转换器的 convertMessage 调用。它失败了,因为我使用星形投影并试图限制 T 的类型,但这导致编译器认为 convertMessage 接受 Message
这样的代码在 Kotlin 中是否可行?或者我应该使用类似的替代方法吗?
谢谢, 杰夫
【问题讨论】:
-
如果您使用星形投影并显式转换为您要返回的类型,您仍然可以在 Kotlin 中执行相当于滥用原始类型的操作。