在写 Java 程序的时候遇到了如下格式的逻辑: if (s instanceof FunctionDef) { ... } else if (s instanceof ClassDef) { ... } else if (s instanceof Return) { ... } ...
对于这种代码该如何重构才能使得程序看上去更加简洁并且高效?
|  |      1knightdf      2016-04-12 09:23:15 +08:00 换成 Scala 用 match case, 哈哈 | 
|  |      2ahmiao      2016-04-12 09:24:15 +08:00  1 统一接口+子类化? | 
|      3wanghaa      2016-04-12 09:31:49 +08:00 | 
|  |      4gqlxj1987      2016-04-12 09:34:01 +08:00 工厂+策略模式 | 
|  |      5zhuangzhuang1988      2016-04-12 09:40:53 +08:00 import java.util.HashMap; import java.util.LinkedList; import java.util.List; import java.util.Map; abstract class Validate { abstract boolean validate(Object obj); abstract void process(Object val); } class A { } class B { } class AValidate extends Validate { @Override boolean validate(Object obj) { return obj instanceof A; } @Override void process(Object val) { A a = (A)val; // ... } } class BValidate extends Validate { @Override boolean validate(Object obj) { return obj instanceof B; } @Override void process(Object val) { B a = (B)val; // ... } } public class Main { public static void main(String[] args) { Object a = new A(); Validate[] validates = { new AValidate(), new BValidate() }; for(Validate v: validates ){ if(v.validate(a)){ v.process(a); break; } } } } 试试下. | 
|  |      6beanlam      2016-04-12 09:41:52 +08:00 用多态,一个分支对应一个实现。这种方法对于有大量分支的情况可能不适用,因为要写大量的类。 另外一种模式可以参考《代码大全》第十八章提到的“表驱动模式”。 | 
|      7SpicyCat      2016-04-12 09:42:57 +08:00 @ahmiao 同意用接口加子类。 FunctionDef, ClassDef 和 Return 可以实现同一个接口或者继承同一个父类,假设父类叫 Father, 方法名叫 doSomething(), 然后那三个子类各自实现 doSomething(). 这样代码里只需要调用 Father#doSomething 就可以了。 | 
|  |      8levn      2016-04-12 09:47:56 +08:00  1 改成一种更加复杂难懂的方式 | 
|  |      9cxshun      2016-04-12 09:49:57 +08:00 面向接口编程,多态就是这个时候用的。 | 
|  |      10fwrq41251      2016-04-12 09:54:58 +08:00 访问者模式。 或者用 java8 ,有个叫 javaslang 的类库,有用于类型匹配的类。 | 
|  |      11SoloCompany      2016-04-12 09:56:13 +08:00 首选是多态 不适合多态的可以试一下 Kotlin 用 case when 来代替了 if else 而已也没啥区别 | 
|  |      12wanttofly      2016-04-12 10:56:59 +08:00 谢谢回答,最近正好有这方面的修改。 | 
|  |      13hrong      2016-04-12 11:07:10 +08:00 via Android @beanlam 表驱动模式对取值还好,要取函数指针就不合适了, JAVA 不支持函数指针,不知道 java8 能否实现 | 
|  |      15zhuangzhuang1988      2016-04-12 13:37:21 +08:00 或者看这种解决方式, 当然有点难 `functional-programming-in-scala` 作者写的 http://blog.higher-order.com/blog/2009/08/21/structural-pattern-matching-in-java/ | 
|      16kaneg      2016-04-12 14:02:39 +08:00 这不就是多态要解决的问题吗 | 
|  |      17twoyuan      2016-04-12 14:15:25 +08:00 我现在是建一个 Map<Class, Callback> map ,用的时候 map.get(object.class)。不过第一次创建时会慢点 | 
|  |      18Jaylee      2016-04-12 14:18:29 +08:00 这应该是用多态吧 | 
|  |      19laibin      2016-04-12 14:24:26 +08:00 访问者模式。 | 
|  |      20haolly      2016-04-12 14:28:54 +08:00 重構裏面說過,當你看到大量 switch 或者 if-else 的時候,這表示你應該用多態了 |