現象 大量的分支選擇型代碼段看著讓人頭疼 for (Field field : declaredFields) { Class<?> type = field.getType(); String key = field.getName(); Element result = resultMap.ad ...
現象 大量的分支選擇型代碼段看著讓人頭疼
for (Field field : declaredFields) {
Class<?> type = field.getType();
String key = field.getName();
Element result = resultMap.addElement("result");
result.addAttribute("column", StringChangeUtils.CamelhumpToUnderline(key).toLowerCase());
result.addAttribute("property", key);
switch (type.getSimpleName()) {
case "String":
result.addAttribute("jdbcType", "VARCHAR");
break;
case "Integer":
result.addAttribute("jdbcType", "NUMERIC");
break;
case "Double":
result.addAttribute("jdbcType", "NUMERIC");
break;
case "Date":
result.addAttribute("jdbcType", "DATE");
break;
default:
result.addAttribute("jdbcType", "VARCHAR");
break;
}
}
如何重構成為策略模式,由硬編碼的面向過程編程走向面對對象呢
其實很簡單 if裡面的多個魔法常量 和HashMap裡面的key是不是可以等比互換呢!!
所以我們核心就是從一個類似於HashMap這種的容器里去獲取某一個key,就等同於進去到了if 的對應分支
而if 的對應分支 裡面的業務,交給HashMap的Value去調方法完成沒毛病把
第一步抽象化這個if分支的邏輯 ---- 分析
--比如上述代碼是判斷欄位類型 --->通用對象介面是對象類型的·抽象·
-- 那麼這個對象具有什麼能力,就是對應原始if分支的邏輯處理 唄,,
-- 我這裡是根據不同的欄位類型往一個Element元素對象中填充屬性。 -----所以抽出行為為往Element元素對象中填充屬性
第二步抽象化這個if分支的邏輯----- 實現
public interface FileTypeInterfaceStrategy {
void addAttribute(Element element);
}
第三步抽象if分支的種類,不同種類有不同實現,-----分析
1. 比如 類型抽象 有String 類型
2. 比如 類型抽象 有Double 類型
3. 比如 類型抽象 有DATE 類型
4. 等等。。。。。
第四步抽象if分支的種類,不同種類有不同實現,-----實現
- 比如 類型抽象 有String 類型 實現
public class StringStrategy implements FileTypeInterfaceStrategy {
@Override
public void addAttribute(Element element) {
element.addAttribute("jdbcType", "VARCHAR");
}
}
- 比如 類型抽象 有Integer 類型 實現
public class IntegerStrategy implements FileTypeInterfaceStrategy {
@Override
public void addAttribute(Element element) {
element.addAttribute("jdbcType", "NUMERIC");
}
}
- 比如 類型抽象 有Double 類型 實現
public class DoubleStrategy implements FileTypeInterfaceStrategy {
@Override
public void addAttribute(Element element) {
element.addAttribute("jdbcType", "NUMERIC");
}
}
- 比如 類型抽象 有Date 類型 實現
public class DateStrategy implements FileTypeInterfaceStrategy {
@Override
public void addAttribute(Element element) {
element.addAttribute("jdbcType", "DATE");
}
}
- 比如 類型抽象 有其他 類型 實現
public class DefaultStrategy implements FileTypeInterfaceStrategy {
@Override
public void addAttribute(Element element) {
element.addAttribute("jdbcType", "VARCHAR");
}
}
第五步if分支的過程編程已經抽離為對象行為編程----目前如何嵌入業務分析
思考 if選擇分支,第一件事是不是拿到一個值去判斷屬於某一個魔法常量呢!
其實 抽離成對象之後業同理需要知道,這裡的上文行為需要下文的那一個對象的實現去處理。。
比如,上文中拿到String、類型,我需要使用String類型的實現類去調業務方法。
比如,上文中拿到Integer、類型,我需要使用Integer類型的實現類去調業務方法。
if的分支屬性和業務行為被抽離成對象--但是還有個東西沒有抽離,就是IF本身的分支選擇結構沒抽出來 對不對
這時候聯想到第一句話:if本身業務結構還需要抽離-----它本身和HashMaP這種結構類似 是不是可以用它完成替換
第六步if分支的過程編程已經抽離為對象行為編程----目前如何嵌入業務實現
使用工廠方法代理策略的選擇執行:其實很簡單,就是new 一個HashMap,然後把所有的策略對象和Key放入HashMap,使用時候去容器裡面取出來執行業務方法就完事
public class FileTypeStrategyFactory {
private FileTypeStrategyFactory() {
}
private static final FileTypeStrategyFactory bean = new FileTypeStrategyFactory();
public static FileTypeStrategyFactory getBean() {
return bean;
}
/**
* 聲明存儲容器
*/
private static Map<String, FileTypeInterfaceStrategy> factoryMap;
static {
factoryMap = new HashMap<>();
factoryMap.put("String", new StringStrategy());
factoryMap.put("Integer", new IntegerStrategy());
factoryMap.put("Double", new DoubleStrategy());
factoryMap.put("Date", new DateStrategy());
factoryMap.put("default", new DefaultStrategy());
}
public FileTypeInterfaceStrategy getStrategy(String classType) {
return factoryMap.get(classType) != null ? factoryMap.get(classType) : factoryMap.get("default");
}
}
替換原始代碼;
Element resultMap = document.addElement("resultMap");
// 添加根節點屬性
resultMap.addAttribute("id", aClass.getSimpleName() + "Map");
resultMap.addAttribute("type", classForName);
resultMap.addAttribute("extends", "BaseResultMap");
for (Field field : declaredFields) {
Class<?> type = field.getType();
String key = field.getName();
Element result = resultMap.addElement("result");
result.addAttribute("column", StringChangeUtils.CamelhumpToUnderline(key).toLowerCase());
result.addAttribute("property", key);
FileTypeStrategyFactory factory = FileTypeStrategyFactory.getBean();
FileTypeInterfaceStrategy strategy = factory.getStrategy(type.getSimpleName());
strategy.addAttribute(result);
}
策略模式+工廠方法 ----->無縫替換if-else-switch:面向過程---到面向對象是思維的轉變 完結!!!!
作者:隔壁老郭 出處:http://www.cnblogs.com/gtnotgod】/----------隔壁老郭還有大號:隔壁老郭---------------------------------
個性簽名:獨學而無友,則孤陋而寡聞。做一個靈魂有趣的人!
如果覺得這篇文章對你有小小的幫助的話,記得在右下角點個“推薦”哦,博主在此感謝!
萬水千山總是情,打賞一分行不行,所以如果你心情還比較高興,也是可以掃碼打賞博主,哈哈哈(っ•̀ω•́)っ✎⁾⁾!