ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

java-处理继承时删除条件语句

2019-11-21 21:02:04  阅读:214  来源: 互联网

标签:oop java design-patterns refactoring


我想避免使用条件,并应用一些技术来使代码在处理继承的类时更易于维护和扩展.

在这个例子中,我们有.

MarketOrder和LimitOrder都从基类Order扩展.

TradeServiceImpl和getUnitPrice方法,用于计算2个订单将要交易的价格.

此方法有几个条件,可以为不同类型的订单选择正确的价格.此外,它正在转换为派生类.

这种方法的问题在于,如果我要添加5个新Order,则我将拥有7 * 7 = 49 if语句,在其中一些语句中,我将需要转换为一个我可能会与另一个类混淆的派生类.易于编写错误代码,并给我重新设计的感觉.

请问我有什么想法吗?

// Domains.

public class Order{

private OrderTypeEnum orderType; 
// can be buy or sell

public OrderTypeEnum getOrderType() {
    return orderType;
}
public void setOrderType(OrderTypeEnum orderType) {
    this.orderType = orderType;
}
}

public class LimitOrder extends Order{

private Long unitPrice;

public Long getUnitPrice() {
    return unitPrice;
}
public void setUnitPrice(Long unitPrice) {
    this.unitPrice = unitPrice;
}
}

public class MarketOrder extends Order{

}

// Service.

public class TradeServiceImpl implements TradeService{

private TradeRepository tradeRepository;    


public Long getUnitPrice(Order buyOrder, Order sellOrder){

    if(buyOrder instanceof MarketOrder && sellOrder instanceof MarketOrder){
        return tradeRepository.getLastPrice();
    }

    if(buyOrder instanceof MarketOrder && sellOrder instanceof LimitOrder){
        return ((LimitOrder)sellOrder).getUnitPrice();
    }

    if(buyOrder instanceof LimitOrder && sellOrder instanceof MarketOrder){
        return ((LimitOrder)buyOrder).getUnitPrice();
    }

    if(buyOrder instanceof LimitOrder && sellOrder instanceof LimitOrder){
        return ((LimitOrder)buyOrder).getUnitPrice() + ((LimitOrder)sellOrder).getUnitPrice() /2;
    }

    return 0L;
}
}

解决方法:

首先,有两种情况可以合并为一种:当顺序不同时:

 if(buyOrder instanceof MarketOrder && sellOrder instanceof LimitOrder){
        return ((LimitOrder)sellOrder).getUnitPrice();
    }

    if(buyOrder instanceof LimitOrder && sellOrder instanceof MarketOrder){
        return ((LimitOrder)buyOrder).getUnitPrice();
    }

至:

if(!buyOrder.getClass().equals(LimitOrder.getClass())){
        return ((LimitOrder)sellOrder).getUnitPrice();
    }

另一方面,可以将订单类用作包含函数对象的映射的索引.这样,您只需在地图上添加元素即可扩展功能.

您可以使用实现接口的匿名内部类封装计算算法,例如:

public interface IFunction {
    public Long execute(Order oA, Order oB);
}

并使用订单类来决定执行哪些行为来访问此地图:

Map<Class, Map<Class, IFunction>> opClass2calcAlgorithm = new HashMap();

IFunction market_market = new IFunction() {

            @Override
            public Long execute(Order a, Order b) {
                return tradeRepository.getLastPrice();
            }
        };

IFunction market_limit = new IFunction() {

            @Override
            public Long execute(Order a, Order b) {
                return ((LimitOrder)a).getUnitPrice();
            }
        };

Map<Class, IFunction> marketMap = new HashMap();
marketMap.put(MarketOrder.class, market_market);
marketMap.put(LimitOrder.class, market_limit);
opClass2calcAlgorithm.put(marketMap);

最后,您的getUnitPrice方法可以这样实现:

public Long getUnitPrice(Order buyOrder, Order sellOrder){

    long ret = 0L;

    Map<Class, IFunction> firstLevel = opClass2calcAlgorithm.get(buyOrder.getClass());
    if(firstLevel == null) return ret;
    IFunction calcAlg = firstLevel.get(sellOrder.getClass());
    if(calcAlg == null) return ret;

    ret = calcAlg.execute(buyOrder, sellOrder);

    return ret;
}

标签:oop,java,design-patterns,refactoring
来源: https://codeday.me/bug/20191121/2054771.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有