spring 自动注入

Posted 苦逼的人生

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了spring 自动注入相关的知识,希望对你有一定的参考价值。

1.IOC和DI
  IOC侧重的是思想 ,DI实现
  IOC侧重构造对象:通过容器  DI对属性值进行注入  (普通属性和域属性的注入)

2.aop
 第一个案例
       1.增强:前置和后置
             MethodBeforeAdvice    AfterReturningAdvice   接口
           before()              afterRetruing()
       2.增强也需要再xml中进行配置

       3.AOP操作在配置文件中
     <!--dao层的配置-->
    <bean id="someDAO" class="cn.happy.day03aop.dao.SomeDAOImpl"></bean>

    <!--service层的配置-->
    <bean id="someService" class="cn.happy.day03aop.service.SomeServiceImpl">
        <property name="dao" ref="someDAO"></property>
    </bean>

    <!--增强:通知Advice-->
    <bean id="beforeAdvice" class="cn.happy.day03aop.aop.MyBeforeAdvice"></bean>

    切面
    <aop:config>
       <aop:pointcut id="mypointcut" expression="execution(public void doSome())">
       <aop:advisor advice-ref="beforeAdvice" pointcut-ref="mypointcut">
       </aop:advisor>
    </aop:config>

3.切点表达式
    * *..UserServiceImpl.*(..)
     void  全名称 cn.cn.cn.cn.cn.UserServiceImpl.*(..)
     String
     int

 

4.方法签名
     切入点表达式要匹配的对象就是目标方法的方法名。所以,execution表达式中明显就是方法的签名。
     注意:表达式中加[]的部分表示可省略部分,各部分间用空格分开。在其中可以使用以下符号:
      符号              意义
       *                 0至多个任意字符
       ..                用在方法参数中,表示任意多个参数
                         用在包名后,表示当前包及其子包路径
        +                用在类名后,表示当前类及其子类
                         用在接口后,表示当前接口及其实现类
      案例:
        execution(public * *(..))  指定切入点为:任意公共方法
        execution(* set*(..))   指定切入点为:任何一个以"set"开始的方法

 


5.  注入方式
     1.设值注入

     2.构造注入
       条件1:带参构造  无参构造
       条件2:
       <bean id="stu">
           <constructor-arg index="0" value="张三">
       </bean>
  3.p命名空间注入
     1.copy一个p
     2.<bean id="stu" p:name="张三" p:car-ref="car">

4.集合属性注入
   array  set list map properties  k=v
  4.BeanFactory  延迟咱们bean初始化 ,使用的时候再做初始化和ApplicationConext.
  ApplicationConext 是BeanFactory的孙子接口 
  ApplicationConext 容器创建,bean就做初始化

  5.Servlet的初始化时机
    解析:看情况:1.看xml中 load-on-startup 0或者正整数  容器启动,bean已经初始化
                  2.没有的话或者为负数,用户第一次访问Servlet
  6.Spring中Bean作用域 scope="singleton/prototype"

  7.域属性自动注入
     byName:要求:配置文件中可以有多个对象,但是默认只自动装配和属性同名的bean的id对象

     byType:要求:相容类型的对象只能有一个
  

7个专业术语
    增强处理/通知(Advice)
       增强类中的方法
    切入点(Pointcut)
         符合切点表达式的方法才能称为切入点
    连接点(Join Point)
         目标对象中的所有方法都是连接点
    切面(Aspect)
       增强类
    目标对象(Target object)
       等待被增强的对象
    AOP代理(AOP proxy)
        代理对象,内存中创建的。
    织入(Weaving)
      将切面和目标对象进行绑定的过程

注解的DI
 1.什么是注解
   有人说:@Override  在Java中,有小鼠标的就是注解

 2.注解的用法
   @Override 标识子类中的方法一定来源于父类
   @Test  单测方法
   @After 在单测后执行
   @Before 前执行
   @WebServlet(name="" urlpatterns="{"/"}") 对外公开访问地址
   @SuppressWarnings() 取消警告
  
 3.注解主要含义
   解析:注解的本质是接口
   自定义注解
 4.注解的方法 
  解析:注解是给谁看的,Java编译器  Java编译器会获取到注解的类型元数据。对该类或者方法进行特殊的照顾处理
5.基于注解DI(有*和无*)
  component-scan 组件扫描
  base-package="cn.happy.day07annotationdi" 扫描本身和子包
  base-package="cn.happy.day07annotationdi.*" 只扫描子包
@Component  标识一个类是被Spring容器管理的一个bean

分层的情况
@Repository dao
@Service    service
@Controller 控制层
@Value  给类的普通属性赋值
@Resource 给类的域属性赋值
@AutoWired 给类的域属性赋值

金牌结论:如果直接在域属性上写Resource。没有指定名称,先按照byName尝试装配,如果容器中
,没有和成员变量同名的bean,那么继续使用byType进行装配。如果byType
检测到相容的类型有多个,就报错:expected single matching,but found 2;

代理
两类:动态代理和静态代理

静态代理:代理模式
 代理:
  1.代理
    招生的速度加快了
  2.代理
    房屋中介
  3.对原有对象的行为进行增强
   
 抽象主题:Subject:接口
 目标对象(原始对象):RealSubject(要增强的对象) implements 
 代理对象:Proxy(植入目标对象) 实现了接口
           before code block
           business  xxx.invoke()
           after code block

 动态代理 AOP底层实现:有接口自动应用的就是JDK动态代理
     1)JDK  在运行时运行时注入
          本质:在内存中构建出接口的实现类
          特点:被代理对象,必须有接口


        Proxy.newProxyInstance(ClassLoader loader,
                                          Class<?>[] interfaces,
                                          InvocationHandler h)

        InvocationHandler调度处理器
        public interface InvocationHandler {


        }


ClassLoader loader,  类加载器(孙卫琴) 如何获取到类加载器?
Class<?>[] interfaces,
InvocationHandler h  调度处理器

CGLIB动态代理: 编译的时候
      特点:再一个类型没有接口的情况下进行代理
             实质:内存中构建了出了目标类型的子类
             对于不使用接口的业务类,无法使用JDK动态代理,cglib采用非常底层的字节码技术,
         可以为一个类创建子类
CGLIB动态代理  无接口代理 编译已经增强
final SomeServiceImpl service=new  SomeServiceImpl();
Enhancer enhancer=new Enhancer();
enhancer.setSuperClass(service.getClass());
enhancer.setCallBack(new MethodInterceptor(){

   public Object intercept(Object o,Method method,Object[] objects,MethodProxy methodProxy){
    sout("before=========");
    Object resullt=methodProxy.invoke(service,objects);
        return result;
   }
});

SomeServiceImpl proxy=(SomeServiceImpl)enhancer.create();
proxy.doSome();
























































































































































































以上是关于spring 自动注入的主要内容,如果未能解决你的问题,请参考以下文章

Spring引用类型自动注入

spring的两种属性注入方式setter注入和构造器注入或者自动注入

Spring5依赖注入常用的三种方法:构造注入Setter注入自动装配

Spring 3.0 学习-DI 依赖注入_创建Spring 配置-使用一个或多个XML 文件作为配置文件,使用自动注入(byName),在代码中使用注解代替自动注入,使用自动扫描代替xml中bea(

Spring Boot自动注入原理

Spring框架Spring依赖注入DIBean作用域Bean的自动装配