您可以使用枚举,假设消息列表在编译时已知。优点是现在每条消息都负责保存其条件,并且调用代码会简单得多。
public enum Message {
MESSAGE1("Welcome") {
@Override
boolean isApplicable(long totalDays, int x, int y) {
return totalDays < 7 && x < 20;
}
},
MESSAGE2("Bye bye") {
@Override
boolean isApplicable(long totalDays, int x, int y) {
return totalDays < 7 && x > 10 && y < 20;
}
};
private String msg;
Message(String msg) {
this.msg = msg;
}
abstract boolean isApplicable(long totalDays, int x, int y);
public static String lookupMessage(long totalDays, int x, int y) {
for (Message m : Message.values()) {
if (m.isApplicable(totalDays, x, y)) {
return m.msg;
}
}
throw new IllegalArgumentException();
}
}
现在在你的调用代码中,不再有 if / else if,只有一行代码:
System.out.println(Message.lookupMessage(1, 2, 3));
注 1:这不如使用 Map 高效,因为查找是 O(n) 操作,但由于 n 约为 100 左右,因此不会造成显着的性能损失。而且它比其他答案中提出的解决方案更具可读性和可维护性。
注 2:您甚至可以将条件/消息放入平面文件中,在运行时读取该文件并使用脚本引擎在运行时评估每个条件。它会稍微慢一些(但我们在这里讨论的是亚毫秒),但会消除代码中的所有混乱并将其放入配置文件中。