策略模式-简单实现

策略模式

大部分场景,我们喜欢用IF-ELSE 或者swich解决很多问题。如果我们采用策略模式,可以方便很多

比如我们有个场景,需要分析不同文件

Show Your Code

1、定义接口

public interface Parser {
    String parse(String filePath);
}

2、接口实现

/**
 * @desc PDF解析
 **/
@Component(ContentTypeEnum.TypeConstants.PDF_PARSER)
public class PDFParser implements Parser{
    @Override
    public String parse(String filePath) {
        return ContentTypeEnum.TypeConstants.PDF_PARSER;
    }
}
/**
 * @desc 文本解析
 **/
@Component(ContentTypeEnum.TypeConstants.TEXT_PARSER)
public class TextParser implements Parser {
    @Override
    public String parse(String filePath) {
        return ContentTypeEnum.TypeConstants.TEXT_PARSER;
    }
}
/**
 * @desc word解析
 **/
@Component(ContentTypeEnum.TypeConstants.WORD_PARSER)
public class WordParser implements Parser{
    @Override
    public String parse(String filePath) {
        return ContentTypeEnum.TypeConstants.WORD_PARSER;
    }
}

3、定义枚举

import lombok.AllArgsConstructor;
import lombok.Getter;
@Getter
@AllArgsConstructor
public enum ContentTypeEnum {

    WORD(TypeConstants.WORD_PARSER),
    PDF(TypeConstants.PDF_PARSER),
    TEXT(TypeConstants.TEXT_PARSER);
    private  String parserName;

    @Override
    public String toString() {
        return this.parserName;
    }
    public interface TypeConstants {
        /**PDF标识 */
        String PDF_PARSER = "pdfParser";
        /**word标识 */
        String WORD_PARSER = "wordParser";
        /**text标识 */
        String TEXT_PARSER = "textParser";
    }
}

4、客户端定义

@Service
public class ParserClient {
    /**
     * 通过spring IOC bean 构造器注入 Map 
     * 把接口Parser下的实现类,put到map中
     */
    private  final Map<String,Parser> parserMapFactory ;
    public ParserClient(Map<String, Parser> parserMapFactory) {
        this.parserMapFactory = parserMapFactory;
    }
    /**
     * 解析文件
     * @param contentType 解析器类型
     * @param filePath 文档路径
     * @return
     */
    public String parse(ContentTypeEnum contentType,String filePath) {
        return parserMapFactory
                .get(contentType.getParserName())
                .parse(filePath);
    }
}

5、单元测试

@Autowired
    private ParserClient parserClient;
    @Test
    public void test7(){
        System.out.println(parserClient.parse(ContentTypeEnum.WORD,"D:/xxxx.docx"));
    }

打印结果:

wordParser

6、服务定位器模式

另外工厂接口,还可以通过服务定位来声明【Service Locator Pattern

//定义工厂接口
public interface ParserFactory {
  Parser getParser(ContentType contentType);
}
// 配置工厂bean
@Configuration
public class ParserConfig {
    
  @Bean("parserFactory")
  public FactoryBean serviceLocatorFactoryBean() {
    ServiceLocatorFactoryBean factoryBean = new ServiceLocatorFactoryBean();
    // 设置服务定位接口   
    factoryBean.setServiceLocatorInterface(ParserFactory.class);
    return factoryBean;
  }
}

作者:JAVA旭阳
链接:https://juejin.cn/post/7186464211868844093

//客户端使用,有点差异
@Service
public class Client {

  private final ParserFactory parserFactory;
  @Autowired
  public Client(ParserFactory parserFactory) {
    this.parserFactory = parserFactory;
  }
  public List getAll(ContentTypeEnum contentType) {
    ..
    // 关键点,直接根据类型获取
    return parserFactory
        .getParser(contentType)  
        .parse("xxxxxxpath");
  }
  ..
}

作者:JAVA旭阳
链接:https://juejin.cn/post/7186464211868844093
来源:稀土掘金

小结

策略模式:简单使用,扩展添加新的解析器(功能)就行,再也不用修改客户端了,满足开闭原则。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值