我有一个小组项目,我们被迫使用提供的接口和枚举。
想象一下如下情况:
// marker interface
interface Request<T extends Response>{}
// marker interface
interface Response{}
enum TypeAction implements Request<SomeEnumClassThatImplementsResponse>{
TYPE1, TYPE2, TYPE3
}
enum OtherTypeAction implements Request<SomeOtherEnumClassThatImplementsResponse>{
OTHERTYPE1, OTHERTYPE2
}
在其他课程中,我有一个这样的请求列表:List<Request> req = new LinkedList<Request>()
我想做的是:做一个如下所示的开关:
switch(a_request){
CASE TYPE1: ....
CASE TYPE2: ....
CASE TYPE3: ....
CASE TYPE2: ....
CASE OTHERTYPE1: ....
CASE OTHERTYPE2: ....
}
我怎么能设法做到这一点?
重要提示:我无法在接口和枚举中添加方法,但我可以创建实现上面可以看到的接口的新枚举。如果可能的话,我宁愿没有两个能做同样事情的枚举。
编辑:这与可能的重复答案不同,因为我无法在Request接口中添加任何方法,因此我无法在枚举类中实现方法。
提前致谢
答案 0 :(得分:4)
你提到的转换显然不起作用。
我有一个(非常奇怪的)替换:创建一个&#34; helper enum&#34;其中包含列出的所有值,并且具有Map<Request<Request<T extends Response>>, HelperEnum>
,如下所示:
private enum HelperEnum {
TYPE1(TypeAction.TYPE1),
TYPE2(TypeAction.TYPE2),
TYPE3(TypeAction.TYPE3),
OTHERTYPE1(OtherTypeAction.OTHERTYPE1),
OTHERTYPE2(OtherTypeAction.OTHERTYPE2),
private Request<T extends Response> source;
private HelperEnum(Request<T extends Response> source) {
this.source = source;
}
private static Map<Request<T extends Response>, HelperEnum> map;
public static HelperEnum lookUp(Request<SomeEnumClassThatImplementsResponse> source) {
if (map == null) {
map = Arrays.stream(HelperEnum.values())
.collect(Collectors.toMap(x -> x.source, x -> x));
}
return map.get(source);
}
(未经测试!特别是我使用Request<T extends Response>
的地方可能是错的;我必须先测试它们。但你应该明白这一点。)
这样你可以做到
switch(HelperEnum.lookUp(a_request)){
case TYPE1: ....
case TYPE2: ....
case TYPE3: ....
case OTHERTYPE1: ....
case OTHERTYPE2: ....
}
答案 1 :(得分:4)
您可以使用地图而不是开关:
~MyRect()
答案 2 :(得分:1)
很遗憾,您无法将switch
用于实际代码,但可以使用if
语句执行此操作:
final List<Request> req = new LinkedList<>();
for (Request request : req) {
if (TypeAction.TYPE1.equals(request)) {
//code
}
else if (OtherTypeAction.OTHERTYPE1.equals(request)) {
//code
}
}
也许您可以在请求和枚举中添加更多字段,然后您可以等于此字段。
答案 3 :(得分:1)
如果您有某种行为,例如Request
可以触发多个枚举操作或单个操作&#39;实现与其他操作有很大不同,因此您需要一个更灵活的解决方案,您可以采用这种方式:
public enum RequestHandlers {
TYPE1_HANDLER(TypeAction.TYPE1::equals, Request::methodA),
TYPE2_HANDLER(r -> r == TypeAction.TYPE2),
OTHERTYPE1_HANDLER(OtherTypeAction.OTHERTYPE1::equals),
COMMON_HANDLER(x -> true, MyLogger::trace);
private final Predicate<Request<?>> requestFilter; // selects supported requests for this handler
private final Consumer<Request<?>> consumer; // implements this handler's behaviour
private RequestHandlers(Predicate<Request<?>> p, Consumer<Request<?>> consumer) {
this.requestFilter = p;
this.consumer = consumer;
}
private RequestHandlers(Predicate<Request<?>> p) {
this.requestFilter = p;
this.consumer = Request::methodB; // default behaviour for all handlers
}
public static void handle(Request<?>... requests) {
Arrays.stream(RequestHandlers.values())
.forEach(handler -> Arrays.stream(requests)
.filter(handler.requestFilter)
.forEach(request -> handler.consumer.accept(request)));
}
}
请注意,当操作符合给定请求时,条件可由过滤器Predicate
配置,操作可由Consumer
配置。