ITPub博客

首页 > 数据库 > 数据库开发技术 > 一探到底!Spring团队使用的那些设计模式,快来看看你用过哪几个

一探到底!Spring团队使用的那些设计模式,快来看看你用过哪几个

原创 数据库开发技术 作者:服务端技术栈 时间:2023-04-02 17:52:37 0 删除 编辑

作为一枚程序员,如果不知道几个设计模式,出去面试都不好意思说自己技术牛了

不知道兄弟们有没有遇到过设计模式相关的面试题,我还记得很多次的面试经验都涉及到了设计模式相关的题目。

今天咱们就探一探Spring中用到了哪些设计模式。

 一、单例模式

这个设计模式绝对是Spring中使用最多的一个设计模式之一,不接受任何反驳

beans模块,context模块,aop模块,mvc模块等多个模块都能见着他的身影。

最经典的用法就是Spring容器在注册单例bean对象的实现中

//org.springframework.beans.factory.support.DefaultSingletonBeanRegistry#addSingletonprivate final Map<String, Object> singletonObjects = new ConcurrentHashMap<>(256);protected void addSingleton(String beanName, Object singletonObject) {   //加锁   synchronized (this.singletonObjects) {      this.singletonObjects.put(beanName, singletonObject);   }}

兄弟,看到了吧?Spring通过加锁和一个Map保证一个bean名只会注册一个实例(单例)。

二、工厂模式

Spring容器就是使用简单工厂模式设计而成的。通过传入bean的名称或者类型获取bean的实例。

public interface BeanFactory {  Object getBean(String name) throws BeansException;  <T> T getBean(Class<T> requiredType) throws BeansException;}


三、装饰器模式

这个模式也是Spring团队使用比较多的设计模式。

比如下面是一个被装饰了线程执行异常处理能力的Runnable,对Runnable的能力进行了增强。

public class DelegatingErrorHandlingRunnable implements Runnable {
   private final Runnable delegate; private final ErrorHandler errorHandler;
@Override public void run() { try { this.delegate.run(); } catch (UndeclaredThrowableException ex) { this.errorHandler.handleError(ex.getUndeclaredThrowable()); } catch (Throwable ex) { this.errorHandler.handleError(ex); } }

四、代理模式

动态代理模式肯定不陌生,代理模式就是支撑aop模块能够实现的底层技术。

final class JdkDynamicAopProxy implements AopProxy, InvocationHandler, Serializable {
  @Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
try { TargetSource targetSource = this.advised.targetSource; target = targetSource.getTarget(); Object retVal = AopUtils.invokeJoinpointUsingReflection(target, method, args); return retVal;    } }}

五、模版方法模式

说到模版模式,通常的写法是不是定义一个抽象类,将固定的骨架写好,由各自的子类负责实现可变的部分,但是在Spring中不得不提JdbcTemplate,

Spring将执行sql的流程骨架实现,将可变的sql通过回调形式的参数传入,体现了模版方法模式的另外一种实现。JmsTemplate,HibernateTemplate都使用到了这种设计模式。

public void execute(final String sql) throws DataAccessException {      class ExecuteStatementCallback implements StatementCallback<Object>, SqlProvider {      @Override      public Object doInStatement(Statement stmt) throws SQLException {         stmt.execute(sql);         return null;      }      @Override      public String getSql() {         return sql;      }   }   execute(new ExecuteStatementCallback());}


六、策略模式

在Spring中实例化Bean采用了策略模式,可以选择反射或者cglib组件两种策略构造一个类的实例。

七、适配器模式

Spring Mvc模块通过适配器模式将HandlerMapping转换为HandlerAdapter,在HandlerAdapter实现Http请求接收与结果处理。

protected HandlerAdapter getHandlerAdapter(Object handler) throws ServletException {   if (this.handlerAdapters != null) {      for (HandlerAdapter adapter : this.handlerAdapters) {         if (adapter.supports(handler)) {            return adapter;         }      }   }}

八、享元模式

最后一个要介绍的就是享元模式了,如果项目中有一些不变的逻辑,而且使用场景非常多的情况,就像一些Class的元数据信息,这些信息不变,但是经常使用,享元模式类似缓存一样的功能,下次还可以从缓存拿出来继续使用

快看下面SpringMvc模块中参数解析器这种写法,真的是爱了,如果没有使用这种模式,每次http请求过来都重新查找和构造一次参数解析器,那么系统内存和性能将有非常大的挑战。

public class HandlerMethodArgumentResolverComposite implements HandlerMethodArgumentResolver {
   private final List<HandlerMethodArgumentResolver> argumentResolvers = new LinkedList<>(); private final Map<MethodParameter, HandlerMethodArgumentResolver> argumentResolverCache = new ConcurrentHashMap<>(256); @Nullable private HandlerMethodArgumentResolver getArgumentResolver(MethodParameter parameter) { HandlerMethodArgumentResolver result = this.argumentResolverCache.get(parameter); if (result == null) { for (HandlerMethodArgumentResolver resolver : this.argumentResolvers) { if (resolver.supportsParameter(parameter)) { result = resolver; //下次还需要使用,缓存起来 this.argumentResolverCache.put(parameter, result); break; } } }      //缓存存在,直接返回 return result; }}

看到Spring团队使用了这么多设计模式,心中默默的给Spring的大佬们点赞👍,真的把设计模式应用的淋漓尽致

如果您喜欢这个文章,麻烦用您的发财小手一键三连,点赞关注转发就是对我最大的支持。

原文作者:服务端技术栈;如有侵权,请联系管理员删除。

请登录后发表评论 登录
全部评论

注册时间:2019-03-08

  • 博文量
    97
  • 访问量
    41428