【发布时间】:2022-12-08 01:28:15
【问题描述】:
我有以下设置。
interface Initializable<T> {
T getValue();
void setValue(T value);
}
class BaseClass {
private final String code; // has getter and setter
///
}
class StringValue extends BaseClass implements Initializable<String> {
private final String value;
@Override
public void setValue(String value) {
this.value = value;
}
@Override
public String getValue() {
return value;
}
}
class IntValue extends BaseClass implements Initializable<Integer> {
private final Integer value;
@Override
public void setValue(Integer value) {
this.value = value;
}
@Override
public Integer getValue() {
return value;
}
}
class NotInitializable extends BaseClass {
/////
}
我有一个 BaseClass 实例列表,我想为 Initializable 实例设置值字段,如下所示。我希望能够在没有原始使用的情况下做到这一点。我似乎无法完成这项工作。任何帮助表示赞赏。 TIA
List<BaseClass> fields; // populated
Map<String, Object> vauleByCode; // populated
for (final BaseClass bc : fields) {
if (bc instanceof Initializable) {
// I would like to set this value of type Object to the value field in Initializable
final Object value = valueByCode.get(bc.getCode());
// I would not like to use Raw variable here (i. e without the generic ?)
Initializable<?> init = (Initializable<?>) bc;
init.setValue(value) // set value here
}
}
【问题讨论】:
-
第二个代码 sn-p 可能不是您“拥有”的实际“设置”:它有基本的拼写错误 (
vaule),并且它使用的是setValue,没有任何参数。您究竟在哪里检查您从地图中获取的Objects 的实际运行时类型是否与bc-field 的类型相匹配?如果它试图将一个整数设置到String字段中怎么办,然后呢? -
谢谢你的评论!没错,我希望能够使用通用方法或其他方式动态设置它而无需显式检查。
-
此外,自 generics are erased 起,如果不强制转换(因此放弃类型安全),这将无法工作。绑定的
<?>也会产生问题,因为我们无法在运行时确定泛型参数的类型。 -
“我希望能够在不明确检查的情况下动态设置”- 好吧,你告诉编译器的方式是强行将
bc转换为Initializable<Object>,然后调用bc.setValue(value)。