责任树模式

public interface StrategyHandler<T,R> {
    @SuppressWarnings("rawtypes")
    StrategyHandler DEFAULT = t -> null;

    /**
     * apply strategy
     */
    R apply(T param);
}
package com.fanggeek;

import jdk.nashorn.internal.objects.annotations.Getter;
import jdk.nashorn.internal.objects.annotations.Setter;
import org.springframework.stereotype.Component;
import sun.misc.Contended;

import javax.annotation.PostConstruct;
import java.util.Objects;

/**
 * 通用的策略树框架,通过树形结构实现分发和委托,每层通过指定的参数向下分发委托,直到达到最终的执行者。
 * 该框架包括两个类 {@code StrategyHandler}和{@Code AbstractStrategyRouter}
 * 实现{@Code AbstractStrategyRouter}抽象类来完成对策略的分发,
 * 实现{@code StrategyHandler}接口来对策略进行实现
 * 第二层 A,B这样的节点既是策略的实现又要完成策略的分发
 * <pre>
 *           +---------+
 *           |  Root   |   ----------- 第 1 层策略入口
 *           +---------+
 *            /       \  ------------- 根据入参 P1 进行策略分发
 *           /         \
 *     +------+      +------+
 *     |  A   |      |  B   |  ------- 第 2 层不同策略的实现
 *     +------+      +------+
 *       /  \          /  \  --------- 根据入参 P2 进行策略分发
 *      /    \        /    \
 *   +---+  +---+  +---+  +---+
 *   |A1 |  |A2 |  |B1 |  |B2 |  ----- 第 3 层不同策略的实现
 *   +---+  +---+  +---+  +---+
 * </pre>
 * @param <T>
 * @param <R>
 * @author Cwoke
 * @date 2021-5-20
 * @see StrategyHandler
 */
@Component
public abstract class AbstractStrategyRouter<T,R> {

    private StrategyMapper<T,R> strategyMapper;

    @SuppressWarnings("unchecked")
    private StrategyHandler<T, R> defaultStrategyHandler = StrategyHandler.DEFAULT;

    /**
     * 策略映射器,根据入参选择StrategyHandler
     * @param <T>
     * @param <R>
     */
    public interface StrategyMapper<T,R>{
        StrategyHandler<T,R> get(T param);
    }

    /**
     * 执行策略,框架会自动根据策略分发至下游的Handler进行处理
     * @Param param
     */
    public R applyStrategy(T param){
        final StrategyHandler<T,R> strategyHandler =   strategyMapper.get(param);
        if (strategyHandler!=null){
            return strategyHandler.apply(param);
        }
        return defaultStrategyHandler.apply(param);
    }

    /**
     * 类初始化的时候注册分发策略Mapper
     */
    @PostConstruct
    private void abstractInit(){
        strategyMapper = registerStrategyMapper();
        Objects.requireNonNull(strategyMapper,"strategyMapper cant be null");
    }

    /**
     * 抽象方法,需要子类实现策略的分发逻辑
     * @return
     */
    protected abstract StrategyMapper<T, R> registerStrategyMapper();
}

StrategyMapper的作用是用来分发策略,里面维护了get(T param)方法

StrategyHandler的作用是用来处理策略里面维护了apply(T R)的方法。其中StrategyHandler相当于叶子节点用来处理逻辑。

AbstractStategyRouter的作用是用来处理分发策略和处理策略的功能,维护了StrategyMapper和StrategyHandler属性,并且有3个方法,其中抽象方法registerStrategyMapper 和 abstractInit用来在初始化的时候注册分发策略Mapper,是策略图中的A,B的结构,既要分发策略,又要处理策略。applyStarategy方法是用来处理Handler。

posted @ 2021-05-20 20:32  Cwoke  阅读(622)  评论(0)    收藏  举报