代码中太多 if else 怎么办?

640?wx_fmt=jpeg

作者 | 坚持就是胜利
链接 | juejin.im/post/5d12228de51d45775c73dd1b

前言

前段时间,我将公司系统中的批量审单的功能进行了重构,用到了java的并发编程进行异步化处理,数据库的乐观锁机制处理多线程并发更新数据。其中批量审单的业务处理涉及到多种任务类型,对应不同的业务方法进行处理,比如转仓,转快递,添加赠品,删除赠品,拆分订单,批量驳回,批量作废等等,其中就用到了策略模式。

if else模式

  if ("BATCH_CHANGE_WAREHOUSE".equals(taskType)) {	
            //批量转仓逻辑	
        } else if ("BATCH_CHANGE_SHIPPING".equals(taskType)) {	
            //批量转快递逻辑	
        } else if ("BATCH_REPLACE_ORDER_GOODS".equals(taskType)) {	
            //批量替换订单商品逻辑	
        } else if ("BATCH_DELETE_ORDER_GOODS".equals(taskType)) {	
            //批量删除订单商品逻辑	
        } else if ("BATCH_ADD_MEMO".equals(taskType)) {	
            //批量添加备注逻辑	
        } else {	
            //任务类型未知	
            System.out.println("任务类型无法处理");	
        }
看起来,思路清晰,if,else分支也很清楚,但不觉得代码很臃肿,维护起来麻烦吗,尤其是其他人来接锅的时候,连看下去的欲望都没有了。这时候你需要用策略模式消除其中的if else,进行一下简单的重构!

策略模式

1、首先抽象业务处理器

public abstract class InspectionSolver {	
    public abstract void solve(Long orderId, Long userId);	
    public abstract String[] supports();	
}

2、将业务处理器和其支持处理的类型放到一个容器中,java里Map就是最常用的容器之一

@Component	
public class InspectionSolverChooser implements ApplicationContextAware{	

	
    private Map<String, InspectionSolver> chooseMap = new HashMap<>();	

	
    public InspectionSolver choose(String type) {	
        return chooseMap.get(type);	
    }	

	
    @PostConstruct	
    public void register() {	
        Map<String, InspectionSolver> solverMap = context.getBeansOfType(InspectionSolver.class);	
        for (InspectionSolver solver : solverMap.values()) {	
            for (String support : solver.supports()) {	
                chooseMap.put(support,solver);	
            }	
        }	
    }	

	
    private ApplicationContext context;	

	
    @Override	
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {	
        this.context=applicationContext;	
    }	
}
这里是在应用启动的时候,加载spring容器中所有InspectionSolver类型的处理器,放到InspectionSolverChooser的map容器中。注意是InspectionSolver类型,所以定义的处理器都得继承InspectionSolver,其次是spring容器中的才能加载,所以定义的处理器都得放到spring容器中(@Component注解不能少)

3、定义不同的处理器

@Component	
public class ChangeWarehouseSolver extends InspectionSolver {	

	
    @Override	
    public void solve(Long orderId, Long userId) {	
        System.out.println("订单"+orderId+"开始进行批量转仓了。。");	
    }	

	
    @Override	
    public String[] supports() {	
        return new String[] {InspectionConstant.INSPECTION_TASK_TYPE_BATCH_CHANGE_WAREHOUSE};	
    }	
}	

	
@Component	
public class ChangeShippingSolver extends InspectionSolver{	

	
    @Override	
    public void solve(Long orderId, Long userId) {	
        System.out.println("订单"+orderId+"开始进行转快递了。。");	
    }	

	
    @Override	
    public String[] supports() {	
        return new String[] {InspectionConstant.INSPECTION_TASK_TYPE_BATCH_CHANGE_SHIPPING};	
    }	
}	

	
@Component	
public class ReplaceOrderGoodsSolver extends InspectionSolver{	

	
    @Override	
    public void solve(Long orderId, Long userId) {	
        System.out.println("订单"+orderId+"开始进行替换商品了");	
    }	

	
    @Override	
    public String[] supports() {	
        return new String[]{InspectionConstant.INSPECTION_TASK_TYPE_BATCH_REPLACE_ORDER_GOODS};	
    }	
}

4、测试类

@RunWith(SpringJUnit4ClassRunner.class)	
@SpringBootTest(classes=Application.class)// 指定spring-boot的启动类	
public class InspectionTest {	

	
    @Autowired	
    private InspectionSolverChooser chooser;	

	
    @Test	
    public void test() throws Exception{	
        //准备数据	
        String taskType = InspectionConstant.INSPECTION_TASK_TYPE_BATCH_CHANGE_WAREHOUSE;	
        Long orderId = 12345L;	
        Long userId = 123L;	
        //获取任务类型对应的solver	
        InspectionSolver solver = chooser.choose(taskType);	
        if (solver == null) {	
            throw new RuntimeException("任务类型暂时无法处理!");	
        }	
        //调用不同solver的方法进行处理	
        solver.solve(orderId,userId);	
    }	
}
在测试类中我消除了可能一长段的if else,从选择器InspectionSolverChooser中根据type的不同取出不同的任务处理器InspectionSolver,然后调用其solve()方法进行任务处理,不同处理器调用的当然就是不同的solve()方法了,目的达到。

如果喜欢本篇文章,欢迎转发、点赞。关注订阅号「Web项目聚集地」,回复「技术博文」即可获取更多图文教程、技术博文、学习资源。


推荐阅读

1. 

2. 

3. 

4. 

5. 

6. 

7. 

8. 

640?wx_fmt=jpeg

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值