Spring学习(三)——Spring中的依赖注入的方式

【前面的话】

       Spring对我太重要了,做个关于web相关的项目都要使用Spring,每次去看Spring相关的知识,总是感觉一知半解,没有很好的系统去学习一下,现在抽点时间学习一下Spring。不知道为什么对Spring有一种莫名的喜欢感,也许是因为他的名字,有一种希望的感觉。

      Spring学习过程中的总结和心得,本文在学习了什么是依赖注入和AOP以后,继续学习依赖注入的方式,请选择性阅读。

本文由牲口TT在博客园首次发表,转载请保持文章的完整性并注明:
作者:牲口TT
链接:http://www.cnblogs.com/xt0810/p/3628402.html

【相关文章】

Spring学习(一)——Spring中的依赖注入简介

Spring学习(二)——Spring中的AOP的初步理解

【依赖注入方式】

      在前面的两篇文章中,学习了什么是依赖注入,什么是AOP,当然,那两篇文章也只是仅仅介绍什么是的问题,我想再通过学习,理解怎么做的问题,这篇文章就是学习在Spring中依赖注入一般是怎么注入的,注入的方式都有哪些,如果你还不理解什么是依赖注入,最好先读读前面两篇文章。

1. 依赖注入的方式:

1)   设值注入:IOC容器使用属性的setter方法来注入被依赖的实例。

2)   构造注入:IOC容器使用构造器来注入被依赖的实例。

3)   静态工厂注入:IOC容器使用静态工厂方法来注入被依赖的实例。

4)   实例工厂注入方式:IOC容器使用实例工厂方法来注入被依赖的实例。

2. setter注入:

     主要代码如下——完整代码见【四个demo】 。

  • 在Setter这种形式的注入中,Person类并不知道他要实例化的Car类,也就是具体类AuDi类在哪里,他只知道他调用了接口Car,具体的实例化是由Spring来进行的。
  • 在测试中,MainTest类分别写了传统方式,也就是不使用Spring的情形,通过比较可以发现其实下面的等价的:
1 <bean id="person" class="Person">
2        <property name="car" ref="auDi" />
3 </bean>
4 <bean id="auDi" class="AuDi" />

上下等价:

1 Person person=new Person();
2 AuDi audi=new AuDi();
3 person.setCar(audi);

1)   Person.java

 1 public class Person {
 2 
 3     private Car car;
 4     
 5     public void setCar(Car car){
 6         this.car =car;
 7     }
 8         
 9     public void driver(){
10         car.GuaDang();
11         car.CaiYouMen();
12         car.DaFangXiang();
13     }
14 }

2)   MainTest.java

 1 import org.springframework.context.ApplicationContext;
 2 import org.springframework.context.support.ClassPathXmlApplicationContext;
 3 public class MainTest {
 4      public static void main(String[] args){
 5          //setter方式进行依赖注入
 6          //使用Spring依赖注入的方式进行注入
 7          ApplicationContext context = new ClassPathXmlApplicationContext("cartest.xml");
 8          Person boy =(Person) context.getBean("person");
 9          boy.driver();
10          
11          //传统方式进行依赖注入
12          /*Person person=new Person();
13          AuDi audi=new AuDi();
14          person.setCar(audi);
15          person.driver();*/
16          }
17 }

3)   cartest.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <beans xmlns="http://www.springframework.org/schema/beans"
 3     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4     xmlns:p="http://www.springframework.org/schema/p"
 5     xmlns:context="http://www.springframework.org/schema/context"
 6     xsi:schemaLocation="http://www.springframework.org/schema/beans
 7         http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
 8         http://www.springframework.org/schema/context
 9         http://www.springframework.org/schema/context/spring-context-3.0.xsd">    
10     <bean id="person" class="Person">
11         <property name="car" ref="auDi" />
12     </bean>
13     <bean id="auDi" class="AuDi" />
14 </beans>

3. 构造注入:

     主要代码如下——完整代码见【四个demo】 。

  • 在构造注入中,Person类并不知道他要实例化的Car类,也就是具体类AuDi类在哪里,他只知道他调用了接口Car,具体的实例化是由Spring来进行的。
  • 在测试中,MainTest类分别写了传统方式,也就是不使用Spring的情形,通过比较可以发现其实下面的等价的:
1 <bean id="person" class="Person">
2        <constructor-arg ref="Car" />
3 </bean>
4 <bean id="Car" class="AuDi" />

上下等价:

1 AuDi audi=new AuDi();
2 Person person=new Person(audi);

1)   Person.java

 1 public class Person {
 2     private Car car;
 3     public Person(Car car){//构造器注入,传入的是car,也就是一个所有车型都必须实现的接口
 4         this.car =car;//这里可以响应奥迪,宝马等任何一种车的实现。
 5     }//这里Person类没有与任何特定类型的车发生耦合,对于Person来说,任何一种特定的车,只需要实现Car接口即可。具体是哪一种车型,对Person来说无关紧要。
 6     
 7     public void driver(){
 8         car.GuaDang();
 9         car.CaiYouMen();
10         car.DaFangXiang();
11     }
12 }

2)   MainTest.java

1 import org.springframework.context.ApplicationContext;
2 import org.springframework.context.support.ClassPathXmlApplicationContext;
3 public class MainTest {
4      public static void main(String[] args){
5          ApplicationContext context = new ClassPathXmlApplicationContext("cartest.xml");
6          Person boy =(Person) context.getBean("person");
7          boy.driver();
8      }
9 }

3)   cartest.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <beans xmlns="http://www.springframework.org/schema/beans"
 3     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4     xmlns:p="http://www.springframework.org/schema/p"
 5     xmlns:context="http://www.springframework.org/schema/context"
 6     xsi:schemaLocation="http://www.springframework.org/schema/beans
 7         http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
 8         http://www.springframework.org/schema/context
 9         http://www.springframework.org/schema/context/spring-context-3.0.xsd">    
10     <bean id="person" class="Person">
11         <constructor-arg ref="Car" />
12     </bean>
13     <bean id="Car" class="AuDi" />
14 </beans>

4. 静态工厂注入:

      主要代码如下——完整代码见【四个demo】 。

      在MainTest类中就可以看出使用Spring和不使用Spring的区别

1)   CarFactory.java

 1 public class CarFactory {
 2     public static Car getCarInstance(String type){//静态方法,这样做的缺点是如果CarFactory被继承,getCar不能被重写。
 3         Car carInstance = null;
 4         if(type.equals("audi")){
 5             carInstance=new AuDi();
 6         }else if(type.equals("baoma")){
 7             carInstance=new BaoMa();
 8         }
 9         return carInstance;
10     }
11 }

2)   MainTest.java

 1 import org.springframework.context.ApplicationContext;
 2 import org.springframework.context.support.ClassPathXmlApplicationContext;
 3 import org.springframework.beans.factory.xml.XmlBeanFactory;
 4 
 5 public class MainTest {
 6     public static void main(String[] args){
 7         //这是不使用Spring的情况
 8         //如果是静态方法,直接通过类调用方法即可.
 9         /*Car audicar=CarFactory.getCarInstance("audi");
10         audicar.Prepare();
11         audicar.Install();
12         audicar.Color();
13         Car baomacar=CarFactory.getCarInstance("baoma");
14         baomacar.Prepare();
15         baomacar.Install();
16         baomacar.Color();*/
17         
18         //这是使用Spring的情况
19         //如果是静态方法,直接通过类调用方法即可.
20         ApplicationContext context = new ClassPathXmlApplicationContext("cartest.xml");
21         Car caraudi =(Car) context.getBean("audi");
22         caraudi.Prepare();
23         caraudi.Install();
24         caraudi.Color();
25         Car carbaoma =(Car) context.getBean("baoma");
26         carbaoma.Prepare();
27         carbaoma.Install();
28         carbaoma.Color();
29     }
30 }

3)   cartest.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <beans xmlns="http://www.springframework.org/schema/beans"
 3     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4     xmlns:p="http://www.springframework.org/schema/p"
 5     xmlns:context="http://www.springframework.org/schema/context"
 6     xsi:schemaLocation="http://www.springframework.org/schema/beans
 7         http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
 8         http://www.springframework.org/schema/context
 9         http://www.springframework.org/schema/context/spring-context-3.0.xsd">    
10     <bean id="audi" class="CarFactory" factory-method="getCarInstance">
11     <constructor-arg>
12             <value>audi</value>
13     </constructor-arg>
14     </bean>
15     <bean id="baoma" class="CarFactory" factory-method="getCarInstance">
16     <constructor-arg>
17             <value>baoma</value>
18     </constructor-arg>
19     </bean>
20 </beans>

5. 实例工厂注入:

      主要代码如下——完整代码见【四个demo】 。

      在MainTest类中就可以看出使用Spring和不使用Spring的区别。

1)   CarFactory.java

 1 public class CarFactory {
 2     public  Car getCarInstance(String type){//非静态方法
 3         Car carInstance = null;
 4         if(type.equals("audi")){
 5             carInstance=new AuDi();
 6         }else if(type.equals("baoma")){
 7             carInstance=new BaoMa();
 8         }
 9         return carInstance;
10     }
11 }

2)   MainTest.java

 1 import org.springframework.context.ApplicationContext;
 2 import org.springframework.context.support.ClassPathXmlApplicationContext;
 3 import org.springframework.beans.factory.xml.XmlBeanFactory;
 4 
 5 public class MainTest {
 6     public static void main(String[] args){
 7 
 8         //这是不使用Spring的情况
 9         //不是静态方法需要先实例化对象,然后在调用方法。
10         /*CarFactory carfactory =new CarFactory();
11         Car audicar=carfactory.getCarInstance("audi");
12         audicar.Prepare();
13         audicar.Install();
14         audicar.Color();
15         Car baomacar=carfactory.getCarInstance("baoma");
16         baomacar.Prepare();
17         baomacar.Install();
18         baomacar.Color();*/
19         
20         //这是使用Spring的情况
21         //不是静态方法需要先实例化对象,然后在调用方法。
22         ApplicationContext context = new ClassPathXmlApplicationContext("cartest.xml");
23         Car caraudi =(Car) context.getBean("audi");
24         caraudi.Prepare();
25         caraudi.Install();
26         caraudi.Color();
27         Car carbaoma =(Car) context.getBean("baoma");
28         carbaoma.Prepare();
29         carbaoma.Install();
30         carbaoma.Color();
31     }
32 }

3)   cartest.xml

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <beans xmlns="http://www.springframework.org/schema/beans"
 3     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 4     xmlns:p="http://www.springframework.org/schema/p"
 5     xmlns:context="http://www.springframework.org/schema/context"
 6     xsi:schemaLocation="http://www.springframework.org/schema/beans
 7         http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
 8         http://www.springframework.org/schema/context
 9         http://www.springframework.org/schema/context/spring-context-3.0.xsd">    
10     <bean id="carfactory" class="CarFactory"/>
11     <bean id="audi" factory-bean="carfactory" factory-method="getCarInstance">
12     <constructor-arg>
13             <value>audi</value>
14     </constructor-arg>
15     </bean>
16     <bean id="baoma" factory-bean="carfactory" factory-method="getCarInstance">
17     <constructor-arg>
18             <value>baoma</value>
19     </constructor-arg>
20     </bean>
21 </beans>

【四个demo

1. Spring依赖注入使用setter设注入demo

2. Spring依赖注入使用构造设注入demo

3. Spring依赖注入使用静态工厂设注入demo

4. Spring依赖注入使用实例工厂设注入demo

【命名空间】

    《Spring实战》中对于Spring自带了多种XML命名空间,主要如下:

命名空间

用途

aop

为声明切面以及将@AspectJ注解的类代理为Spring切面提供了配置元素

beans

支持声明Bean和装配Bean,是Spring最核心也是最原始的命名空间

context

为配置Spring应用上下文提供了配置元素,包括自动检测和自动装配Bean,注入非Springzhujie

jee

提供了与Java   EE API的集成,例如JNDI和EJB

jms

为声明消息驱动的POJO提供了配置元素

lang

支持配置由Groovy,   JRuby,货BeanShell等脚本实现的Bean

mvc

启用Spring   MVC的能力,例如面向注解的控制器,视图控制器和拦截器

oxm

支持Spring的对象到XML映射配置

tx

提供声明试事务配置

util

提供各种各样的工具类元素,包括把集合配置为Bean,支持属性占位符元素

【参考资料】

     1. 《Spring in action》 Craig Walls著 耿渊 张卫滨译

    2. 《轻量级Java EE 企业应用实战》 李刚著

【后面的话】

     有时感觉自己学习挺快的,有时会发现自己学习的节奏好慢,希望可以通过好好努力学习更多的技能。

分享:

     芭蕉不展丁香结,同向春风各自愁

——TT

 

posted @ 2014-03-27 16:07  赞恩  阅读(2787)  评论(0编辑  收藏  举报