什么是Spring IoC
IoC即“控制反转”的意思,是Spring框架的核心概念之一,它还有另外一个名字DI(Dependency Injection),即依赖注入。“控制反转”的概念有点模糊,通俗的解释就是找个人来为你服务,满足你的需求。比如,想喝鲜榨橙汁,如果自己做需要去水果店买橙子、清洗、扒皮,放到榨汁机里,然后才能喝到橙汁。也可以有另外一种方法,你到水果店旁边的咖啡厅,直接点一杯鲜榨橙汁,两分钟后你就可以喝到。换句话说就是主动创造到被动接收服务的过程。
传统的面向对象的Java程序设计,被注入的对象直接依赖于被依赖的对象,被注入的对象就是“我”,“想喝橙汁”是“我”的需求,被依赖的对象是“橙子”。被注入的对象直接依赖于依赖的对象,可以翻译为我想喝橙汁就要依赖于我有橙子。引入Spring IoC之后,提供了IoC Service Provider来管理和维护被注入对象与被依赖对象之间的关系。IoC Service Provider就是“咖啡厅”,当我想喝橙汁时,我只需要到咖啡厅说一声来杯橙汁,当我想喝咖啡时,我也只需要到咖啡厅说一声来杯咖啡。从而屏蔽了买橙子,买咖啡豆的过程。我更省事了。
IoC的优点和缺点
从上面的例子可以开出来,IoC的优点就是省事儿了,但是这种省事儿是相对的。操作上变简单了,但是底层逻辑变复杂了。一方面,IoC打破了传统的Java SE程序在对象使用前必须创建的模式,就好像有了JVM后,我们不在过多考虑对象销毁回收一样,有了IoC,我们无需考虑对象的创建。而另一方面显而易见,对象的创建过程更加复杂了,以前了解JVM内存结构,了解Class的加载过程以及Java的基本语法,基本就能弄清楚new对象的生命周期了。但是现在除了这些,还需要弄清楚Spring bean的管理机制。同时,由于对象的创建过程变复杂了,因此相对来说性能上有些损耗。但是,相对于Spring IoC带来的灵活性相比,这点性能消耗无关紧要。
IoC实例
为了能更好的介绍IoC,还是借助上面喝橙汁的例子,用一个简单的Java程序进行说明如下:
package com.ioctest.spring;
public interface Juice {
void buyFruit();
void doJuice();
}
package com.ioctest.spring;
public class OrangeJuice implements Juice {
public void buyFruit() {
System.out.println("买橙子");
}
public void doJuice() {
System.out.println("榨橙汁");
}
}
package com.ioctest.spring;
public class PearJuice implements Juice {
public void buyFruit() {
System.out.println("买梨子");
}
public void doJuice() {
System.out.println("榨梨汁");
}
}
package com.ioctest.spring;
public class Factory {
public final static String ORANGEJUICE = "OrangeJuice";
public final static String PEARJUICE = "PearJuice";
public Juice getJuice(String fruit) {
if (fruit.equals(ORANGEJUICE)) return new OrageJuice;
else if (fruit.equals(PEARJUICE)) return new PearJuice;
else throw new IllegalArgumentException("参数输入错误!");
}
}
package com.ioctest.spring;
public class JuiceTest {
public static void main(String[] args) {
Juice juice = null;
juice = new Factory().getJuice(Factory.ORANGEJUICE);
juice.buyFruit();
juice.doJuice();
juice = new Factory().getJuice(Factory.PEARJUICE);
juice.buyFruit();
juice.doJuice();
}
}
使用Spring IoC的用法如下
在项目根目录下创建bean.xml文件
<?xml version="1.0" encoding="UTF-8"?>
<beans
xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.0.xsd">
<bean id="OrangeJuice" class="com.ioctest.spring.OrangeJuice"/>
<bean id="PearJuice" class="com.ioctest.spring.PearJuice"/>
</beans>
新的测试代码如下:
package com.ioctest.spring;
public class JuiceTest {
public final static String ORANGEJUICE = "OrangeJuice";
public final static String PEARJUICE = "PearJuice";
public static void main(String[] args) {
ApplicationContext ctx =
new FileSystemXmlApplicationContext("bean.xml");
Juice juice = null;
juice = (Juice)ctx.getBean(ORANGEJUICE);
juice.buyFruit();
juice.doJuice();
}
}