• 不用注入方式使用Spring管理的对象中的方法,神奇


    在小冷工作中遇到这么一个小问题,当你的业务层对象交给spring管理之后,在普通的类中调用这个类中的方法时候,会有个问题这个类在调用时候会一直返回一个null,而且还会抛出一个空指针异常。

    小冷在遇到这个问题时候使用了各种方法发现很多都不能用,其中小冷罗列下生效的方法,并且网上还推荐使用的

    1.在普通类种也将自己注入交给spring管理

    首先看上面的,第一张图片,那个普通类似交给了spring管理的,并在这个类中注入了使用的业务层类,这个时候调用这个类中的方法时候,发现这个业务类返回是一个null,至于原因小冷下面解释。

    还有一种

    2.小冷使用实例化这个业务类,一般实例化的类会加入堆内存的这样试一下发现也不行

    3.使用类加载的方式将加载器在项目启动时就调用这个加载器,然后通过加载后的spring类加载器调用加载,这种是可以的

    综上所述只有第三种方法可以,这个里附上加载spring容器的中的实例化类的工具类

    package com.util;
    /*
     * @desc:提供非SPRING管理类调用管理类的功能
     * 注意在服务启动的时候进行import,apllication中引入
     */
    import org.springframework.beans.BeansException;
    import org.springframework.context.ApplicationContext;
    import org.springframework.context.ApplicationContextAware;
    import org.springframework.stereotype.Component;
    ​
    ​
    @Component
    public class SpringUtil implements ApplicationContextAware {
           private static ApplicationContext applicationContext = null;
    ​
           @Override
    ​
           public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
    ​
                  if (SpringUtil.applicationContext == null) {
                         SpringUtil.applicationContext = applicationContext;
                  }
                  System.out.println("---------------------------------------------------------------------");
                  System.out.println("========ApplicationContext配置成功,在普通类可以通过调用SpringUtils.getAppContext()获取applicationContext对象,applicationContext=" + SpringUtil.applicationContext + "========");
                  System.out.println("---------------------------------------------------------------------");
           }
    ​
           //获取applicationContext
           public static ApplicationContext getApplicationContext() {
                  return applicationContext;
           }
    ​
           //通过name获取 Bean.
           public static Object getBean(String name) {
                  return getApplicationContext().getBean(name);
           }
    ​
           //通过class获取Bean.
           public static <T> T getBean(Class<T> clazz) {
                  return getApplicationContext().getBean(clazz);
           }
    ​
           //通过name,以及Clazz返回指定的Bean
           public static <T> T getBean(String name, Class<T> clazz) {
                  return getApplicationContext().getBean(name, clazz);
           }
    }

    使用方式工具类中有注释;就不一一赘述

    这里小冷按自己理解说一下为啥前两种方式无法使用,如有不同理解和更为准确的解释欢迎私信留言!!!!关注我公众号“秦川以北”

    先说一下第一种:小冷理解在看源码时候是由于在使用@Component注解和@Autowired时注入的实例未初始化,这时候spring容器中接收不到未初始化的实例,这个解决方案,在注入的同时初始化这个实例让spring扫描到这个实例然后加入容器

    @Component
    public class ComponentClass {
    ​
        @Autowired
        private JedisClient jedisClient;
        public static ComponentClass componentClass;
        @PostConstruct
        public void init(){
            componentClass = this;
            componentClass.jedisClient = this.jedisClient;
        }
    }

    第二种:第二种事由于实例化的业务类在自己类种引用了spring容器种的实例类,这个时候实例化的类在堆内存种,而spring容器在自己的堆存种中,他们不在同一个堆中可能这是实例化失效的关键。

    以上都是小冷个人理解如有不同见解欢迎留言怼,有的源码小冷也是看的一知半解。

  • 相关阅读:
    Linux下安装nginx
    使用Nginx搭建集群
    怎样解决虚拟机中多台机器之间的相互通信问题??
    怎样安装vmtools
    常用的机器学习&数据挖掘知识(点)领域链接
    sparkan安装链接
    matlab中怎样将散点用光滑曲线连接起来??
    matlab中怎样画出散点图,将这些散点连接成线??
    matlab中怎样计算两个集合的差集?-setdiff函数
    MATLAB中在一个三维矩阵中如何提取出一个二维矩阵,使用permute
  • 原文地址:https://www.cnblogs.com/qinyuanyuan/p/13406962.html
Copyright © 2020-2023  润新知