spring学习3-Ioc和DI的简单介绍

控制反转(Inversion of Control,英文缩写为IoC)是一个重要的面向对象编程的法则来削减计算机程序的耦合问题,也是轻量级的Spring框架的核心。 控制反转还有一个名字叫作依赖注入(Dependency Injection)。简称DI程序员

以上是来自于百度百科中关于IOC和DI的简单介绍,从中咱们能够看到ioc的主要做用是减小类与类之间的耦合程度,在spring中,ioc的表现为类的实例化由本来程序员本身建立对象的动做转为由spring容器建立对象。web

在不使用IOC的状况下,咱们实例化一个类spring

  
IEngine engine = new QiyouEngine();

在这个语句中咱们用到了IEngine接口和其实现类QiyouEngine,这样这个类就须要引用这两个类,若是须要改动实现类,则须要修改代码,这就违反了面向对象设计中的”开闭原则“。想要解耦这段代码,通常的解决可使用工厂模式对其解耦编程

  
1 public class Main{ 2 public static void main(String args[]){ 3 IEngine engine = EngineFactory.getEngine(); 4 engine.doSomething(); 5 } 6 } 7 8 9 public class EngineFactory{ 10 public static getEngine(){ 11 return new QiyouEngine(); 12 } 13 }

若是再进一步,可使用工厂模式+配置文件+反射来实现session

好比咱们的配置文件叫config.property,里面配置app

engine=com.example.QiyouEngine;框架

在工厂中咱们就能够修改为ide

  
1 public class EngineFactory { 2 3 public static IEngine getEngine() throws Exception{ 4 // 读取配置文件 5 Properties prop = new Properties(); 6 String rootPath = System.getProperty( " user.dir " ); 7 File f = new File(rootPath + File.separator + " config " + File.separator + " config.property " ); 8 InputStream in = new BufferedInputStream( new FileInputStream(f)); 9 prop.load(in); 10 String className = prop.getProperty( " engine " ); 11 12 // 根据反射得到类 13 IEngine engine = (IEngine) Class.forName(className).newInstance(); 14 return engine; 15 } 16 }

这样只要修改配置文件中的实现类名就能够修改程序中的实现类,从而达到不用修改代码的目的。学习

和上面的例子类似,spring也有着本身的配置文件。this

这里我在src目录下建立了一个applicationContext.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 xsi:schemaLocation ="http://www.springframework.org/schema/beans 5 http://www.springframework.org/schema/beans/spring-beans.xsd" > 6 7 < bean id ="engine" class ="com.demo.spring.car.QiyouEngine" > 8 </ bean > 9 </ beans >

 

在代码中咱们能够这么写:

  
1 public static void main( String[] args ) 2 { 3 ApplicationContext context = new ClassPathXmlApplicationContext( " applicationContext.xml " ); 4 IEngine engine = (IEngine) context.getBean( " engine " ); 5 engine.doSomething(); 6 }

这和刚刚的效果是同样的。

若是你们在找IOC的时候通常都会伴随着DI这个词,在spring中,ioc和di是紧密联系的,下面咱们演示一下DI是什么样子的。

如今有一个类叫QiyouEngine,其中有个属性是发动机的排量cc,若是通常的写法,咱们会在对象建立后经过调用set方法,把值塞到对象中,在spring中能够在配置文件中实现。咱们修改一下刚刚xml文件在engine bean中添加属性:

  
< bean id ="engine" class ="com.demo.spring.car.QiyouEngine" > < property name ="cc" value ="2.0" ></ property > </ bean >

在代码中咱们加入cc成员变量,并为其添加set的方法

  
1 public class QiyouEngine implements IEngine { 2 3 private String cc; // 排量 4 5 public String getCc() { 6 return cc; 7 } 8 9 public void setCc(String cc) { 10 this .cc = cc; 11 } 12 13 public void description() { 14 System.out.println( " 我是汽油发动机\n " + this .toString()); 15 } 16 17 @Override 18 public String toString() { 19 return " QiyouEngine [cc= " + cc + " ] " ; 20 } 21 22 }

在建立完对象后,spring会自动调用set的方法把值塞入对象中。

再运行一边Main类,结果以下

image

固然,咱们注入的不知是常量,也能够注入其余的类。

好比如今咱们有一个类叫Car,它有两个属性,一个是name,另外一个是engine,咱们要作的就是把刚刚的QiyouEngine注入到Car中

  
< bean id ="car" class ="com.demo.spring.car.Car" > < property name ="name" value ="宝马" ></ property > < property name ="engine" ref ="engine" ></ property > </ bean >

图片中能够看到engine用的是ref,而不是value,这个就是引用其余类的关键

main类咱们修改一下,直接得到car类

  
public static void main( String[] args ) { ApplicationContext context = new ClassPathXmlApplicationContext( " applicationContext.xml " ); Car car = (Car) context.getBean( " car " ); System.out.println(car); }

Car类的定义

  
public class Car { private IEngine engine; private String name; public String getName() { return name; } public void setName(String name) { this .name = name; } public IEngine getEngine() { return engine; } public void setEngine(IEngine engine) { this .engine = engine; } @Override public String toString() { return " Car [engine= " + engine + " , name= " + name + " ] " ; } }

运行结果:

image

 

在bean标签里其实还有个属性scope,这个属性能够说是标识这个经过spring ioc获取的类的生命周期,其默认值是单例(Singleton),不过咱们执行多少次context.getBean(“engine”),得到的都是同一个对象,这个属性一共有四个值

  • singleton:单例(默认)
  • prototype:每次调用一次getBean方法,就new一个对象出来
  • request:用于web开发将bean放入request中,在同一个request中获取的是同一个bean
  • session:用于web开发将bean放入session中。

有关ioc和DI跟深刻的使用,待我学习完再和你们分享。

相关文章
相关标签/搜索