常用设计模式概括

开发中会经常用到的设计模式:
(只为了记录在开发中经常会使用到的设计模式,不是为了分析每种设计模式,勿喷)

1 责任链模式:

实现方式一般通过链表,把各个能处理的子类给串起来,看实力,来源于阿里
的开源框架 sentitle:

public interface ProcessorSlot {

    void process(Context context) throws Throwable;


    void nextProcess(Context context) throws Throwable;

}

抽象类

public abstract class AbstractLinkedProcessorSlot implements ProcessorSlot{
    private AbstractLinkedProcessorSlot next = null;

    @Override
    public void nextProcess(Context context)
            throws Throwable {
        if (next != null) {
            next.process(context);
        }
    }



    public AbstractLinkedProcessorSlot getNext() {
        return next;
    }

    public void setNext(AbstractLinkedProcessorSlot next) {
        this.next = next;
    }

}

各个实现类

public class AuthoritySlot extends AbstractLinkedProcessorSlot{
    @Override
    public void process(Context context) throws Throwable {
        System.out.println("来源访问控制:slot,param:"+context.getParam());
        String param = context.getParam();
        if (param.equals("end")){
            System.out.println("processor end...");
            return;
        }
        nextProcess(context);
    }
}
public class ClusterBuilderSlot extends AbstractLinkedProcessorSlot{
    @Override
    public void process(Context context) throws Throwable {
        System.out.println("统计簇点构建:slot,param:"+context.getParam());
        context.setParam("end");
        nextProcess(context);
    }


}
public class DegradeSlot extends AbstractLinkedProcessorSlot{
    @Override
    public void process(Context context) throws Throwable {
        System.out.println("熔断降级:slot,param:"+context.getParam());
        nextProcess(context);
    }


}
public class FlowSlot extends AbstractLinkedProcessorSlot{
    @Override
    public void process(Context context) throws Throwable {
        System.out.println("流量控制:slot,param:"+context.getParam());
         context.setParam("end");
         nextProcess(context);
    }
}

组装的链子

public abstract class ProcessorSlotChain extends AbstractLinkedProcessorSlot {
    /**
     * Add a processor to the head of this slot chainreposbile.
     *
     * @param protocolProcessor processor to be added.
     */
    public abstract void addFirst(AbstractLinkedProcessorSlot protocolProcessor);

    /**
     * Add a processor to the tail of this slot chainreposbile.
     *
     * @param protocolProcessor processor to be added.
     */
    public abstract void addLast(AbstractLinkedProcessorSlot protocolProcessor);
}

默认组装链的实现

public class DefaultProcessorSlotChain extends ProcessorSlotChain {

    AbstractLinkedProcessorSlot first = new AbstractLinkedProcessorSlot() {

        @Override
        public void process(Context context)
                throws Throwable {
            super.nextProcess(context);
        }
    };
    AbstractLinkedProcessorSlot end = first;

    @Override
    public void addFirst(AbstractLinkedProcessorSlot protocolProcessor) {
        protocolProcessor.setNext(first.getNext());
        first.setNext(protocolProcessor);
        if (end == first) {
            end = protocolProcessor;
        }
    }

    @Override
    public void addLast(AbstractLinkedProcessorSlot protocolProcessor) {
        end.setNext(protocolProcessor);
        end = protocolProcessor;
    }

    /**
     * Same as {@link #addLast(AbstractLinkedProcessorSlot)}.
     *
     * @param next processor to be added.
     */
    @Override
    public void setNext(AbstractLinkedProcessorSlot next) {
        addLast(next);
    }

    @Override
    public AbstractLinkedProcessorSlot getNext() {
        return first.getNext();
    }

    @Override
    public void process(Context context)
            throws Throwable {
        first.process(context);
    }
}

链子生成器

public interface SlotChainBuilder {
    ProcessorSlotChain build();
}

实现

public class DefaultSlotChainBuilder implements SlotChainBuilder {
    @Override
    public ProcessorSlotChain build() {
        ProcessorSlotChain chain = new DefaultProcessorSlotChain();
        chain.addLast(new ClusterBuilderSlot());
        chain.addLast(new AuthoritySlot());
        chain.addLast(new FlowSlot());
        chain.addLast(new DegradeSlot());

//        chain.addFirst(new NodeSelectorSlot());
//        chain.addFirst(new ClusterBuilderSlot());
//        chain.addFirst(new LogSlot());
//        chain.addFirst(new StatisticSlot());
//        chain.addFirst(new SystemSlot());
//        chain.addFirst(new AuthoritySlot());
//        chain.addFirst(new FlowSlot());
//        chain.addFirst(new DegradeSlot());

        return chain;
    }
}

扩展主要通过不同的生成器来实现,比如可以提供一个provider

public class InterceptorChainProvider {

    private InterceptorChainProvider(){}

    private static volatile InterceptorChain chain = null;

    private static final Object LOCK = new Object();

    /**
     * new instance interceptor chain
     * @return InterceptorChain
     */
    public static InterceptorChain newInterceptorChain(InterceptorChainBuilder builder){
        if (chain==null){
            synchronized (LOCK){
                if (chain==null){
                    if (builder==null){
                        log.warn("current builder is null,so use default builder");
                        builder = new DefaultInterceptorChainBuilder();
                    }
                    chain = builder.builder();
                }
            }
        }
        log.info("init interceptor chain:{}",chain);
        return chain;
    }
}

2.过滤器链设计模式

主要用来做多个操作的过滤处理,看实例

public interface Filter {
	void doFilter(Request request, Response response, FilterChain chain);
}

实现:

public class HTMLFilter implements Filter {
	
	@Override
	public void doFilter(Request request, Response response, FilterChain chain) {
		//process the html tag <>
		request.requestStr = request.requestStr.replace('<', '[')
				   .replace('>', ']') + "---HTMLFilter()";
		chain.doFilter(request, response, chain);
		response.responseStr += "---HTMLFilter()";
	}
}
public class SesitiveFilter implements Filter {
	@Override
	public void doFilter(Request request, Response response, FilterChain chain) {
		request.requestStr = request.requestStr.replace("", "")
		 .replace("", "") + "---SesitiveFilter()";
		chain.doFilter(request, response, chain);
		response.responseStr += "---SesitiveFilter()";
	}
}

过滤器链:

public class FilterChain implements Filter {
	List<Filter> filters = new ArrayList<Filter>();
	int index = 0;
	
	public FilterChain addFilter(Filter f) {
		this.filters.add(f);
		return this;
	}
	
	@Override
	public void doFilter(Request request, Response response, FilterChain chain) {
		if(index == filters.size()) return ;
		
		Filter f = filters.get(index);
		index ++;
		f.doFilter(request, response, chain);
	}
}

测试

public class Main {
	/**
	 * @param args
	 */
	public static void main(String[] args) {
		String msg = "";
		Request request = new Request();
		request.setRequestStr(msg);
		Response response = new Response();
		response.setResponseStr("response");
		FilterChain fc = new FilterChain();
		fc.addFilter(new HTMLFilter())
		  .addFilter(new SesitiveFilter())
		  ;
		
		fc.doFilter(request, response, fc);
		System.out.println(request.getRequestStr());
		System.out.println(response.getResponseStr());
	}
}

3.事件模式

事件模式中的几个概念

事件源:事件的触发者,比如上面的注册器就是事件源。

事件:描述发生了什么事情的对象,比如上面的:xxx注册成功的事件

事件监听器:监听到事件发生的时候,做一些处理,比如上面的:路人A、路人B

使用场景:
完成核心业务之后,还需要做其它业务的处理,但是这写业务并非是核心的,针对这些非核心业务的处理,就可以使用事件监听来处理了

注意:如果对于这些非核心的业务处理不能有失败的可能,那么可以考虑使用消息中间件来解决

主要实现流程分析:
1 定义一个抽象事件源
2 定义一个实现抽象事件源的具体事件源,可以是多个
3 定义一个事件源监听处理器
4 定义一个事件广播器或事件发布器(主要包含 发布事件,增加事件,移除事件)
5 定义一个实现具体事件源处理器的具体业务

备注:核心业务和事件监听处理,最好不要用一个线程来处理,最好分成异步来处理的,因为有时候如果监听事件的处理比较耗时
会阻塞核心业务。

实例:
定义抽闲事件:

public abstract class AbstractEvent {
    protected Object source;

    public Object getSource() {
        return source;
    }

    public void setSource(Object source) {
        this.source = source;
    }

    public AbstractEvent(Object source){
        this.source = source;
    }
}

事件监听器

public interface EventListener<E extends AbstractEvent> {
    void onEvent(E event);
}

事件广播器

public interface EventMulticaster {

    /**
     * 广播事件给所有的事件监听者,并做相应的处理
     * @param event
     */
    void multicastEvent(AbstractEvent event);

    /**
     * 添加事件监听器
     * @param eventListener
     */
    void addEventListener(EventListener<?> eventListener);

    /**
     * 移除事件监听器
     * @param eventListener
     */
    void removeEventListener(EventListener<?> eventListener);
}

测试:实现用户注册功能

public class UserRegisterService {

    private EventMulticaster eventMulticaster;

    public EventMulticaster getEventMulticaster() {
        return eventMulticaster;
    }

    public void setEventMulticaster(EventMulticaster eventMulticaster) {
        this.eventMulticaster = eventMulticaster;
    }

    public void userRegister(String username){
        System.out.println(String.format("用户【%s】注册成功", username));
        this.eventMulticaster.multicastEvent(new UserRegisterSuccessEvent(this,username));
    }
}

定义注册事件

public class UserRegisterSuccessEvent extends AbstractEvent {
    private String username;


    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public UserRegisterSuccessEvent  (Object source,String username){
        super(source);
        this.username = username;
    }
}

发邮件监听:

public class SendMailEventListener implements EventListener<UserRegisterSuccessEvent>{
    public void onEvent(UserRegisterSuccessEvent event) {
        System.out.println(String.format("给用户【%s】发送注册成功邮件!",event.getUsername()));
    }
}

发优惠券监听:

public class CouponEventListener implements EventListener<UserRegisterSuccessEvent>{
    public void onEvent(UserRegisterSuccessEvent event) {
        System.out.println(String.format("给用户【%s】发送优惠券!",event.getUsername()));
    }
}

简单广播事件的实现:

public class SimpleEventMulticaster implements EventMulticaster{

    /**
     * 一类事件源对应多个事件监听器
     */
    private Map<Class<?>, List<EventListener>> eventObjectEventListenerMap = new ConcurrentHashMap<Class<?>, List<EventListener>>();

    /**
     * 广播事件给所有的事件监听者,并做相应的处理
     *
     * @param event
     */
    public void multicastEvent(AbstractEvent event) {
        List<EventListener> eventListeners = this.eventObjectEventListenerMap.get(event.getClass());
        if (eventListeners!=null){
            for (EventListener eventListener : eventListeners){
                eventListener.onEvent(event);
            }
        }
    }

    /**
     * 添加事件监听器
     *
     * @param eventListener
     */
    public void addEventListener(EventListener<?> eventListener) {
        Class<?> eventType = this.getEventType(eventListener);
        List<EventListener> eventListeners = this.eventObjectEventListenerMap.get(eventType);
        if (eventListeners==null){
            eventListeners = new ArrayList<EventListener>();
            this.eventObjectEventListenerMap.put(eventType,eventListeners);
        }
        eventListeners.add(eventListener);
    }

    /**
     * 移除事件监听器
     *
     * @param eventListener
     */
    public void removeEventListener(EventListener<?> eventListener) {
        Class<?> eventType = this.getEventType(eventListener);
        List<EventListener> eventListeners = this.eventObjectEventListenerMap.get(eventType);
        if (null!=eventListeners){
            eventListeners.remove(eventListener);
        }
    }

    /**
     * 获取事件监听器需要监听的事件类型
     * @param eventListener
     * @return
     */
    protected Class<?> getEventType(EventListener eventListener){
        ParameterizedType parameterizedType = (ParameterizedType)eventListener.getClass().getGenericInterfaces()[0];
        Type eventType = parameterizedType.getActualTypeArguments()[0];
        return (Class<?>) eventType;
    }
}

事件测试:

public class EventTest {
    public static void main(String[] args) {
        UserRegisterService userRegisterService = new UserRegisterService();
        //事件广播器
        EventMulticaster eventMulticaster = new SimpleEventMulticaster();
        //添加事件源对应的监听器
        eventMulticaster.addEventListener(new SendMailEventListener());
        eventMulticaster.addEventListener(new CouponEventListener());
        //给具体的业务类绑定事件广播器
        userRegisterService.setEventMulticaster(eventMulticaster);
        userRegisterService.userRegister("jiahp");
    }
}

4.拦截器或插件设计模式

来源于mybatis中的部分设计源码,主要执行一些和业务无关或者在处理某个业务之前或之后增加一些额外的工作。具体看实例

public interface Interceptor {

  Object intercept(Invocation invocation) throws Throwable;

  default Object plugin(Object target) {
    return Plugin.wrap(target, this);
  }

  default void setProperties(Properties properties) {
    // NOP
  }

}

拦截器链

public class InterceptorChain {

  private final List<Interceptor> interceptors = new ArrayList<>();

  public Object pluginAll(Object target) {
    for (Interceptor interceptor : interceptors) {
      target = interceptor.plugin(target);
    }
    return target;
  }

  public void addInterceptor(Interceptor interceptor) {
    interceptors.add(interceptor);
  }

  public List<Interceptor> getInterceptors() {
    return Collections.unmodifiableList(interceptors);
  }

}

注解标识

@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
public @interface Intercepts {
  Signature[] value();
}

@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({})
public @interface Signature {
  Class<?> type();

  String method();

  Class<?>[] args();
}

封装拦截方法执行的参数

public class Invocation {

  private final Object target;
  private final Method method;
  private final Object[] args;

  public Invocation(Object target, Method method, Object[] args) {
    this.target = target;
    this.method = method;
    this.args = args;
  }

  public Object getTarget() {
    return target;
  }

  public Method getMethod() {
    return method;
  }

  public Object[] getArgs() {
    return args;
  }

  public Object proceed() throws InvocationTargetException, IllegalAccessException {
    return method.invoke(target, args);
  }

}

实现动态代理的handler

package interceptor;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;


/**
 * @author Clinton Begin
 */
public class Plugin implements InvocationHandler {

  private final Object target;
  private final Interceptor interceptor;
  private final Map<Class<?>, Set<Method>> signatureMap;

  private Plugin(Object target, Interceptor interceptor, Map<Class<?>, Set<Method>> signatureMap) {
    this.target = target;
    this.interceptor = interceptor;
    this.signatureMap = signatureMap;
  }

  public static Object wrap(Object target, Interceptor interceptor) {
    Map<Class<?>, Set<Method>> signatureMap = getSignatureMap(interceptor);
    Class<?> type = target.getClass();
    Class<?>[] interfaces = getAllInterfaces(type, signatureMap);
    if (interfaces.length > 0) {
      return Proxy.newProxyInstance(
          type.getClassLoader(),
          interfaces,
          new Plugin(target, interceptor, signatureMap));
    }
    return target;
  }

  @Override
  public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
    try {
      Set<Method> methods = signatureMap.get(method.getDeclaringClass());
      if (methods != null && methods.contains(method)) {
        return interceptor.intercept(new Invocation(target, method, args));
      }
      return method.invoke(target, args);
    } catch (Exception e) {
      throw new RuntimeException(e);
    }
  }

  private static Map<Class<?>, Set<Method>> getSignatureMap(Interceptor interceptor) {
    Intercepts interceptsAnnotation = interceptor.getClass().getAnnotation(Intercepts.class);
    // issue #251
    if (interceptsAnnotation == null) {
      throw new PluginException("No @Intercepts annotation was found in interceptor " + interceptor.getClass().getName());
    }
    Signature[] sigs = interceptsAnnotation.value();
    Map<Class<?>, Set<Method>> signatureMap = new HashMap<>();
    for (Signature sig : sigs) {
      Set<Method> methods = signatureMap.computeIfAbsent(sig.type(), k -> new HashSet<>());
      try {
        Method method = sig.type().getMethod(sig.method(), sig.args());
        methods.add(method);
      } catch (NoSuchMethodException e) {
        throw new PluginException("Could not find method on " + sig.type() + " named " + sig.method() + ". Cause: " + e, e);
      }
    }
    return signatureMap;
  }

  private static Class<?>[] getAllInterfaces(Class<?> type, Map<Class<?>, Set<Method>> signatureMap) {
    Set<Class<?>> interfaces = new HashSet<>();
    while (type != null) {
      for (Class<?> c : type.getInterfaces()) {
        if (signatureMap.containsKey(c)) {
          interfaces.add(c);
        }
      }
      type = type.getSuperclass();
    }
    return interfaces.toArray(new Class<?>[interfaces.size()]);
  }

}

异常

public class PluginException extends RuntimeException {

  private static final long serialVersionUID = 8548771664564998595L;

  public PluginException() {
    super();
  }

  public PluginException(String message) {
    super(message);
  }

  public PluginException(String message, Throwable cause) {
    super(message, cause);
  }

  public PluginException(Throwable cause) {
    super(cause);
  }
}

具体实例
模拟实现日志监控拦截

@Intercepts({@Signature(type = Executor.class, method = "query", args = {String.class})})
public class LoggingInterceptor implements Interceptor {
    @Override
    public Object intercept(Invocation invocation) throws Throwable {
        Method method = invocation.getMethod();
        Object[] args = invocation.getArgs();
        Object target = invocation.getTarget();
        System.out.println("method:"+method.getName()+",args:"+args);
        return invocation.proceed();
    }

    @Override
    public void setProperties(Properties properties) {

    }

    @Override
    public Object plugin(Object target) {
        if (target instanceof Executor) {
            return Plugin.wrap(target, this);
        }
        return target;
    }
}

模拟实现耗时拦截:

@Intercepts({@Signature(type = Executor.class, method = "query", args = {String.class})})
public class TimeInterceptor implements Interceptor {
    @Override
    public Object intercept(Invocation invocation) throws Throwable {

        System.out.println("currentTime:"+System.currentTimeMillis());
        return invocation.proceed();
    }

    @Override
    public void setProperties(Properties properties) {

    }

    @Override
    public Object plugin(Object target) {
        if (target instanceof Executor) {
            return Plugin.wrap(target, this);
        }
        return target;
    }
}

5.委派或装饰器模式

该模式组合为:模版方法+委派模式

写法:有的叫Delegate,有的叫Wrapper

功能:类似于装饰器,对原有接口功能进行扩展或增强处理

实例:mybatis,对于查询使用了缓存(一级和二级),是否使用缓存,需要看isEnabledCache是否为true,如果为true,所有的查询操作都会缓存,
否则不走缓存,给查询加缓存的功能,它就使用了委派模式,自己只负责加缓存,至于内部的查询它并不负责,还是有各个对应的执行器自己来实现。

dubbo中的protocol,就是用了此模式对协议进行了一些列的过滤拦截ProtocolFilterWrapper

看代码

public interface Executor {
    /**
     *
     * @param param
     * @param <T>
     * @return
     */
    <T> T query(String param);
}

模版实现

public abstract class AbstractExecutor implements Executor {

    /**
     *
     * @param param
     * @param <T>
     * @return
     */
    @Override
    public <T> T query(String param) {
        //做点其它事情
        return doQuery(param);
    }

    protected abstract  <T> T doQuery(String param);
}

子类实现

public class BatchExecutor extends AbstractExecutor {

    @Override
    protected <T> T doQuery(String param) {
        System.out.println("批量查询");
        return null;
    }
}

public class CacheExecutorDelegate implements Executor {

    private Executor executor;

    public CacheExecutorDelegate(Executor executor){
        this.executor = executor;
    }

    public <T> T query(String param) {
        //首先从缓存里面取
        loadCacheFromOne(param);
        loadCacheFromTwo(param);
        return executor.query(param);
    }


    private void loadCacheFromOne(String param){
        System.out.println("查询之前:从一级缓存加载数据");
    }


    private void loadCacheFromTwo(String param){
        System.out.println("查询之前:从二级缓存加载数据");
    }
}

public class ReuseExecutor extends AbstractExecutor {

    @Override
    protected <T> T doQuery(String param) {
        System.out.println("复用查询");
        return null;
    }
}


public class SimpleExecutor extends AbstractExecutor {

    @Override
    protected <T> T doQuery(String param) {
        System.out.println("单次查询");
        return null;
    }
}

执行器工厂

public class ExecutorFactory {

    private static volatile Executor executor = null;

    public static Executor getExecutor(String type, boolean isCached) {

        Executor executor = null;

        if (executor == null) {
            synchronized (ExecutorFactory.class) {
                if (executor == null) {
                    if (type.equals("simple")) {
                        executor = new SimpleExecutor();
                    } else if (type.equals("batch")) {
                        executor = new BatchExecutor();
                    } else if (type.equals("reuse")) {
                        executor = new ReuseExecutor();
                    }


                    if (isCached) {
                        executor = new CacheExecutorDelegate(executor);
                    }

                    return executor;
                }
            }
        }
        return executor;

    }
}

测试:

public class ExecutorTest {
    public static void main(String[] args) {

        InterceptorChain interceptorChain = new InterceptorChain();
        interceptorChain.addInterceptor(new LoggingInterceptor());
        interceptorChain.addInterceptor(new TimeInterceptor());
        interceptorChain.addInterceptor(new SqlExplainInterceptor());

        Executor simpleExecutor = ExecutorFactory.getExecutor("simple", false);
        Executor  simpleInterceptorExecutor= (Executor)interceptorChain.pluginAll(simpleExecutor);
        simpleInterceptorExecutor.query("");

//        System.out.println("=================================");
//        Executor batch = ExecutorFactory.getExecutor("batch", true);
//        batch.query("");
    }
}

6.master-worker模式

Master-Worker模式是常用的并行设计模式。核心思想是,系统由两个角色组成,Master和Worker,Master负责接收和分配任务,
Worker负责处理子任务。任务处理过程中,Master还负责监督任务进展和Worker的健康状态;
Master将接收Client提交的任务,并将任务的进展汇总反馈给Client

Master-Worker模式满足于可以将大任务划分为小任务的场景,是一种分而治之的设计理念。
通过多线程或者多进程多机器的模式,可以将小任务处理分发给更多的CPU处理,
降低单个CPU的计算量,通过并发/并行提高任务的完成速度,提高系统的性能
看实例:
定义master对象

package master.work;

import java.util.HashMap;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentLinkedQueue;

/**
 * @author hpjia.abcft
 * @version 1.0
 * @date 06-28
 * @description 封装任务+worker+写回每个worker执行的结果集
 */
public class Master {

    /**
     * 封装任务的队列
     */
    private ConcurrentLinkedQueue<Product> productConcurrentLinkedQueue = new ConcurrentLinkedQueue<Product>();

    /**
     * 封装work数量
     */
    private Map<String,Thread> workerThread = new HashMap<String, Thread>(100000);

    /**
     * 保存每个worker执行的结果
     */
    private ConcurrentHashMap<String,Object> workerRunResult = new ConcurrentHashMap<String, Object>();


    public Master(Worker worker,int workCount){
        worker.setProductConcurrentLinkedQueue(productConcurrentLinkedQueue);
        worker.setWorkerRunResult(workerRunResult);
        for (int i=0;i<workCount;i++){
            this.workerThread.put(Integer.toString(i),new Thread(worker));
        }
    }


    /**
     * submit 任务提交
     */
    public void submit(Product product){
        this.productConcurrentLinkedQueue.add(product);
    }

    /**
     * execute 任务执行
     */
    public void execute(){
        for (Map.Entry<String, Thread> entry:workerThread.entrySet()){
            entry.getValue().start();
        }
    }

    /**
     * isEnd 线程是否执行结束
     */
    public boolean isComplete(){
        for (Map.Entry<String, Thread> entry:workerThread.entrySet()){
            if (entry.getValue().getState()!=Thread.State.TERMINATED){
                return false;
            }
        }
        return true;
    }

    /**
     * getResult 获取执行结果
     */

    public int getResult() {
        int priceResult = 0;
        for(Map.Entry<String, Object> me : this.workerRunResult.entrySet()){
            priceResult += (Integer)me.getValue();
        }
        return priceResult;
    }
}

处理的实体

public class Product {
    private int prdId;
    private int prdPrice;
    public int getPrdId() {
        return prdId;
    }
    public void setPrdId(int prdId) {
        this.prdId = prdId;
    }
    public int getPrdPrice() {
        return prdPrice;
    }
    public void setPrdPrice(int prdPrice) {
        this.prdPrice = prdPrice;
    }

    @Override
    public String toString() {
        return "商品信息: 商品id " + prdId + ", 商品价格" + prdPrice+"元" ;
    }
}

定义抽象的干活worker

package master.work;

import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentLinkedQueue;

/**
 * @author hpjia.abcft
 * @version 1.0
 * @date 06-28
 * @description 模拟实现商品定价的单个线程
 */
public abstract class Worker implements Runnable {

    /**
     * 定义一个并发队列用来存储要处理的商品信息
     */

    private ConcurrentLinkedQueue<Product> productConcurrentLinkedQueue;


    public void setProductConcurrentLinkedQueue(ConcurrentLinkedQueue<Product> productConcurrentLinkedQueue) {
        this.productConcurrentLinkedQueue = productConcurrentLinkedQueue;
    }

    public void setWorkerRunResult(ConcurrentHashMap<String, Object> workerRunResult) {
        this.workerRunResult = workerRunResult;
    }

    /**
     * 定义一个存储每个work执行对应的结果
     */
    private ConcurrentHashMap<String,Object> workerRunResult;

    /**
     * When an object implementing interface <code>Runnable</code> is used
     * to create a thread, starting the thread causes the object's
     * <code>run</code> method to be called in that separately executing
     * thread.
     * <p>
     * The general contract of the method <code>run</code> is that it may
     * take any action whatsoever.
     *
     * @see Thread#run()
     */
    public void run() {
        while (true){
            Product product = this.productConcurrentLinkedQueue.poll();
            if (product==null){
                break;
            }
            Object handle = handle(product);
            System.out.println("线程 "+Thread.currentThread().getName()+" , 计算完毕"+ product);
            this.workerRunResult.put(Integer.toString(product.getPrdId()),handle);
        }
    }

    /**
     * 有真正实现产品定价的业务组件来实现
     * @param input
     * @return
     */
    protected abstract Object handle(Product input) ;
}

真正干活的worker

package master.work;

/**
 * @author hpjia.abcft
 * @version 1.0
 * @date 06-28
 * @description 真正实现商品定价的功能的业务逻辑
 */
public class ProductWork extends Worker {


    @Override
    protected Object handle(Product input) {
        Object output = null;
        try {
            //模拟耗时的操作
            Thread.sleep(100);
            output = input.getPrdPrice();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return output;
    }
}

测试代码

package master.work;

import java.util.Random;

/**
 * @author hpjia.abcft
 * @version 1.0
 * @date
 * @description
 */
public class Test {
    public static void main(String[] args) {
        //实例化master
        Master master = new Master(new ProductWork(),500);

        Random r = new Random();
        //10000 个任务
        for(int i = 1; i <= 10000; i++){
            Product t = new Product();
            t.setPrdId(i);
            t.setPrdPrice(r.nextInt(1000));
            //添加任务
            master.submit(t);
        }
        //执行任务
        master.execute();
        long start = System.currentTimeMillis();

        while(true){
            //所有线程执行完毕
            if(master.isComplete()){
                long end = System.currentTimeMillis() - start;
                int priceResult = master.getResult();
                System.out.println("最终结果:" + priceResult + ", 执行时间:" + end+" ms");
                break;
            }
        }
    }
}

7.工厂方法+模版方法+策略模式+面板模式

这种模式在实际项目中经常会使用到,我们看一下模块代码,主要是结合spring来实现的
比如实际项目中一个功能会有多个处理器来处理,根据不同的处理类型,来选择对应的处理策略
定义处理的接口

public interface TransformProcessor  extends InitializingBean {
    /**
     * processorTransform
     * @param processorParam processorParam
     * @return Object
     * @exception Exception
     */
    Map<String,Object> processorTransform (ProcessorParam processorParam) throws Exception;
}

模版实现

public abstract class AbstractTransformProcessor implements TransformProcessor{

    @Override
    @SuppressWarnings("unchecked")
    public Map<String,Object> processorTransform(ProcessorParam processorParam)throws Exception {
        Objects.requireNonNull(processorParam.getRecord(),"transform record is not null");
        Objects.requireNonNull(processorParam.getTransformRule(),"transform rule is not null");
        TransformRule transformRule = processorParam.getTransformRule();
        String fieldName = transformRule.getFieldName();
        Map<String,Object> resultMap = Maps.newHashMap();
        Object result = doTransform(processorParam);
        if (result!=null){
            if (result instanceof Map){
                resultMap = (Map<String,Object> )result;
            }
            else {
                resultMap.put(fieldName,result);
            }
        }
        return resultMap;
    }

    /**
     * ONE FIELD VS MULTI RULE
     * @param processorParam processorParam
     * @exception  throws Exception
     * @return TransformRuleResult
     */
    protected abstract Object doTransform (ProcessorParam processorParam) throws Exception;

}

看具体的处理实例

@Slf4j
@Component
public class ExpressionTransformProcessor extends AbstractTransformProcessor {
    private static final Integer FOUR_EIGHT = 48;
    private static final Integer FIVE_SEVEN = 57;

    /**
     * ONE FIELD VS MULTI RULE
     *
     * @param processorParam processorParam
     * @return TransformRuleResult
     */
    @Override
    protected Object doTransform(ProcessorParam processorParam) {
        log.info("use ExpressionTransformProcessor ...");
        return null;
    }
   @Override
    public void afterPropertiesSet() throws Exception {
        TransformProcessorFactory.registerProcessor(RuleType.FOUR_ARITHMETIC_TYPE.name(), this);
    }
}

@Slf4j
@Component
public class GlobalTransformProcessor extends AbstractTransformProcessor{
    /**
     * ONE FIELD VS MULTI RULE
     *
     * @param processorParam processorParam
     * @return TransformRuleResult
     */
    @Override
    protected Map<String,Object> doTransform(ProcessorParam processorParam) {
        return null;
    }


    @Override
    public void afterPropertiesSet() throws Exception {
      TransformProcessorFactory.registerProcessor(RuleType.GLOBAL_DEFAULT_TYPE.name(),this);
    }
}

@Slf4j
@Component
public class HalfSqlTransformProcessor extends AbstractTransformProcessor {
    @Autowired
    @Qualifier("dpuJdbcTemplate")
    private JdbcTemplate jdbcTemplate;

    /**
     * ONE FIELD VS MULTI RULE
     * <pre>
     *     SELECT
     * 	CASE
     * 		WHEN CHAR_LENGTH(${ddd}) > '3' THEN 'ok'
     * 		ELSE 'no ok' END AS 'error'
     * 	FROM
     * 		dual;
     *     <pre/>
     * @param processorParam processorParam
     * @return TransformRuleResult
     */
    @Override
    protected Object doTransform(ProcessorParam processorParam) {
        log.info("do HalfSqlTransformProcessor....");
        return null;
    }
  @Override
    public void afterPropertiesSet() throws Exception {
        TransformProcessorFactory.registerProcessor(RuleType.HALF_SQL_TYPE.name(),this);
    }
   }

注册工厂:

public class TransformProcessorFactory {

    private TransformProcessorFactory () {}

    private static Map<String,AbstractTransformProcessor> TRANSFORM_PROCESSOR_MAP = Maps.newTreeMap();


    public static void registerProcessor (String type,AbstractTransformProcessor abstractTransformProcessor){
        TRANSFORM_PROCESSOR_MAP.put(type,abstractTransformProcessor);
    }

    public static AbstractTransformProcessor getProcessor(String type){
        return TRANSFORM_PROCESSOR_MAP .get(type);
    }
}

处理器的面板:

@Slf4j
public class TransformProcessorFacade {

    public static Map<String,Object> getProcessorResult(Input input, TransformRule transformRule, TaskMessage taskMessage)throws Exception{
        ProcessorParam.ProcessorParamBuilder builder = ProcessorParam.builder();
        if (null!=taskMessage){
            builder.taskMessage(taskMessage);
        }
        ProcessorParam.ProcessorParamBuilder processorParam = builder.transformRule(transformRule).record(input);
        AbstractTransformProcessor processor = TransformProcessorFactory.getProcessor(transformRule.getRuleType().name());
        return processor.processorTransform(processorParam.build());
    }
}

对应的规则处理类型

public enum RuleType {
    /**
     * SQL
     */
    SQL_TYPE,
    /**
     * HALF SQL
     */
    HALF_SQL_TYPE,
    /**
     * FOUR
     */
    FOUR_ARITHMETIC_TYPE,
    /**
     * GLOBAL
     */
    GLOBAL_DEFAULT_TYPE
}

8.SPI机制
主要是通过插件的形式进行扩展,主要体现在dubbo,sharding jdbc,skywalking三个框架

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值