Java使用Map+函数式接口实现策略模式

一、项目背景

在项目中,我们处理了各种类型的通知消息。在没有采用策略模式之前,代码中充斥了大量的 if-else 语句,这不仅让整个项目显得杂乱无章,还增加了后续维护的难度。为了解决这一问题,我们采用了 Map 和函数式接口来实现策略模式,从而显著提升了代码的可读性和可维护性。
例如下面这样,大家是不是经常见到


if (type == 1) {
	// 业务1
}
else if (type == 2){
    // 业务2
}
else {
    // 业务3
}

开源地址,大家可以点点⭐

二、代码实现

  1. 首先我们创建一个实现各个操作的service,模拟业务操作。
import org.springframework.stereotype.Service;

@Service
public class NoticeTypeService {

    public String email(String name){
        return "电子邮件通知:" + name;
    }
 
    public String QQ(String name){
        return "QQ通知:" + name;
    }

    public String ding(String name){
        return "钉钉通知:" + name;
    }

    public String wechat(String name){
        return "微信通知:" + name;
    }
 
}
  1. 接着我们创建一个策略实现类,代码已写注释。还有不懂得可以评论区提问~
import com.demo.template.service.NoticeTypeService;
import org.springframework.stereotype.Component;

import javax.annotation.PostConstruct;
import javax.annotation.Resource;
import java.util.HashMap;
import java.util.Map;
import java.util.function.Function;

@Component
public class NoticeStrategy {

    @Resource
    private NoticeTypeService noticeTypeService;

    private Map<String, Function<String, String>> noticeTypeMap = new HashMap<>();

    /**
     * 初始化noticeTypeMap @PostConstruct会在bean的依赖注入完成之后被调用
     */
    @PostConstruct
    public void init() {
        noticeTypeMap.put("qq", name -> noticeTypeService.QQ(name));
        noticeTypeMap.put("email", name -> noticeTypeService.email(name));
        noticeTypeMap.put("ding", name -> noticeTypeService.ding(name));
        noticeTypeMap.put("wx", name -> noticeTypeService.wechat(name));
    }

    /**
     * 根据不同的通知类型获取执行结果
     *
     * @param noticeType 通知类型
     * @return noticeTypeService对应函数执行完的结果
     */
    public String getAction(String noticeType, String name) {
        // 从map中取出对应的函数
        Function<String, String> result = noticeTypeMap.get(noticeType);
        if (result != null) {
            return result.apply(name);
        }
        return "不存在此类型";
    }
}

  1. 最后我们创建一个controller,然后测试一下结果
import com.demo.template.config.NoticeStrategy;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;

@RestController
@RequestMapping("/notice")
public class NoticeController {

    @Resource
    private NoticeStrategy strategy;


    @GetMapping("/getType")
    public String getWork(String type,String name) {
        return strategy.getAction(type,name);
    }
}

三、补充

有时候我们的函数需要传入多个参数的,可以自定义函数接口类,下面是示例

/**
 * 自定义参数函数接口,想拓展几个就拓展几个,默认的Function只能传1个参数
 * @param <paramA>
 * @param <paramB>
 * @param <Result>
 */
@FunctionalInterface
interface NoticeFunction<paramA, paramB, Result>{
    Result apply(paramA a, paramB b);
}

四、最终效果

我们在地址栏输入下面的URL,最后浏览器显示如下
http://localhost:8888/api/notice/getType?type=qq&name=张三
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

每天吃八顿

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值