使用泛型与实现相同接口的枚举类的集合 [英] Using generics with collection of enum classes implementing same interface
问题描述
我正在尝试在几个枚举类上进行反向查找通过使用Guava的 Class es列表来实现相同的 Field
接口。 github.io/guava/releases/snapshot/api/docs/com/google/common/collect/Maps.html#uniqueIndex%28java.lang.Iterable,%20com.google.common.base.Function%29rel = nofollow noreferrer> Maps.uniqueIndex
:
I am trying to do reverse lookup on few enum classes implementing same Field
interface by iterating through list of Class
es using Guava's Maps.uniqueIndex
:
Field valueOfSearchName = null;
for (final Class<? extends Enum<?>> clazz : ImmutableList.of(
EntityField.class,
AddressField.class,
PersonFunctionType.class)) {
valueOfSearchName = Fields.valueOfSearchName(clazz, term.field()); // error
if (valueOfSearchName != null) {
// do something...
break;
}
}
我不想重复相同的代码(对于在所有枚举类中制作索引和执行查找),所以我使用包含 Fields.valueOfSearchName
方法的辅助静态类 Fields
:
I don't want to repeat same code (for making index and doing lookup) in all enum classes, so I use helper static class Fields
containing Fields.valueOfSearchName
method:
public static <E extends Enum<E> & Field> Field valueOfSearchName(
final Class<E> clazz, final String searchName) {
// TODO: cache the index
final ImmutableMap<String, E> index = Maps.uniqueIndex(
EnumSet.allOf(clazz), GET_SEARCH_NAME_FUNCTION);
return index.get(searchName);
}
不幸的是,Eclipse显示错误:
Unfortunately, Eclipse shows an error:
Bound mismatch:
The generic method valueOfSearchName(Class<E>, String) of type Fields is not
applicable for the arguments (Class<capture#1-of ? extends Enum<?>>, String).
The inferred type capture#1-of ? extends Enum<?> is not a valid substitute
for the bounded parameter <E extends Enum<E> & Field>
问题是类< ;?扩展Enum<?>> clazz
in-each循环(不匹配Field),但我不知道如何处理这种情况(显然我不能添加& Field
到 clazz
)。
The problem is Class<? extends Enum<?>> clazz
in for-each loop (not matching Field), but I don't know how to deal with this case (obviously I cannot add & Field
to clazz
).
推荐答案
灵感来自 Tom Hawtin的回答我创建了包含 Class
es的包装类,但仅限于那些带有签名< E extends Enum< E> &安培;字段>
:
Inspired by Tom Hawtin's answer I created wrapper class holding Class
es, but only those with signature <E extends Enum<E> & Field>
:
public final static class FieldEnumWrapper<E extends Enum<E> & Field> {
private final Class<E> clazz;
private final ImmutableMap<String, E> index;
public static <E extends Enum<E> & Field>
FieldEnumWrapper<E> of(final Class<E> clazz) {
return new FieldEnumWrapper<E>(clazz);
}
private FieldEnumWrapper(final Class<E> clazz) {
this.clazz = clazz;
this.index = Maps.uniqueIndex(
EnumSet.allOf(clazz), new Function<E, String>() {
@Override
public String apply(final E input) {
return input.searchName();
}
});
}
public Class<E> clazz() {
return clazz;
}
public Field valueOfSearchName(final String searchName) {
return index.get(searchName);
}
}
现在:
for (final FieldEnumWrapper<?> fieldEnum : ImmutableList.of(
FieldEnumWrapper.of(EntityField.class),
FieldEnumWrapper.of(AddressField.class),
FieldEnumWrapper.of(PersonFunctionType.class))) {
valueOfSearchName = fieldEnum.valueOfSearchName("POD_I_OS_PARTNER");
// ...
是类型安全的和不恰当的使用 FieldEnumWrapper
的静态工厂:
is type-safe and inappropriate usage of FieldEnumWrapper
's static factory:
FieldEnumWrapper.of(NotEnumAndFieldClass.class)
生成编译错误。
此外, valueOfSearchName
现在是 FieldEnumWrapper
的方法,这对辅助类更有意义。
Moreover, valueOfSearchName
is now method of FieldEnumWrapper
what make more sense that helper class.
这篇关于使用泛型与实现相同接口的枚举类的集合的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!