spring框架已经熟知了很久了,可是一直没有对其奥秘进行探究,今天我们就来学一下Spring框架的ioc实践:
IoC 全称为 Inversion of Control,翻译为 “控制反转”,它还有一个别名为 DI(Dependency Injection),即依赖注入。
- 谁控制谁?
- 控制是什么?
- 为何是反转?
- 哪些地方反转了?
一、IOC的定义:
由Spring IOC容器来负责对象的生命周期和对象之间的关系。使用Spring核心组件把对象的创建交给了IOC容器,这样使得在修改和更新的时候只需要修改配置文件即可。
常规代码:
一个简单的例子:以找对象为例子,一般情况找对象是怎么样子的呢?首先肯定是根据我们自己的需求来找塞,比如好看,温柔,性格好等属性,然后到处打听她的兴趣爱好等,然后再投其所好,然后到手,用代码表示就是这样:
public class YoungMan {
private BeautifulGirl beautifulGirl;
YoungMan(){
// 可能你比较牛逼,指腹为婚
// beautifulGirl = new BeautifulGirl();
}
public void setBeautifulGirl(BeautifulGirl beautifulGirl) {
this.beautifulGirl = beautifulGirl;
}
public static void main(String[] args){
YoungMan you = new YoungMan();
BeautifulGirl beautifulGirl = new BeautifulGirl("你的各种条件");
beautifulGirl.setxxx("各种投其所好");
// 然后你有女票了
you.setBeautifulGirl(beautifulGirl);
}
}
通常情况,我们如果需要对象,我们一般都是采用new一个对象这种方式,但是这个过程复杂而又繁琐,而且我们必须要面对各个环节,同时用完之后我们还需要销毁他们,在这种情况下我们的对象就和它依赖的的对象耦合在一起。
但是我们思考一个问题?我们每次用到自己依赖的对象真的需要自己去创建吗?我们知道,我们依赖对象其实并不是依赖该对象本身,而是依赖它所提供的服务,只要在我们需要它的时候,它能够及时提供服务即可,至于它是我们主动去创建的还是别人送给我们的,其实并不是那么重要。再说了,相比于自己千辛万苦去创建它还要管理、善后而言,直接有人送过来是不是显得更加好呢
这个给我们送东西的人就是IOC,在上面的例子中,IOC就相当于一个婚介所,这个婚介所管理者很多男男女女的资料,当我们需要一个女朋友的时候,直接跟婚介所提我们的要求就可以了。
现在在看上面那四个问题,答案就显得非常明显了:
- 谁控制谁:在传统的开发模式下,我们都是采用直接 new 一个对象的方式来创建对象,也就是说你依赖的–对象直接由你自己控制,但是有了 IOC 容器后,则直接由 IoC 容器来控制。所以“谁控制谁”,当然是 IoC 容器控制对象。
- 控制什么:控制对象。
- 为何是反转:没有 IoC 的时候我们都是在自己对象中主动去创建被依赖的对象,这是正转。但是有了 IoC 后,所依赖的对象直接由 IoC 容器创建后注入到被注入的对象中,依赖的对象由原来的主动获取变成被动接受,所以是反转。
- 哪些方面反转了:所依赖对象的获取被反转了。
来,看一下代码如何实现:
1.首先定义一个接口:
package com.jiekou;
public interface UserDao {
public void add();
}
2. 新建一个实现该接口的类
package com.classes;
import com.jiekou.UserDao;
public class UserDaoImpl implements UserDao {
@Override
public void add() {
System.out.println("运行重写的add了");
}
}
3. 再新建一个调用这个类的类
package com.classes;
import com.jiekou.UserDao;
public class UserService {
UserDao dao;
public UserService(UserDao dao) {
this.dao = dao;
}
void pp(){
dao.add();
}
}
4.最主要的要来了,新建配置文件,并写入bean配置
<?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.xsd">
<!--Spring入门配置-->
<!--如果有一个新的接口实现类,如果要修改,那么就不用一个一个去修改了。可以在xml配置文件里
进行修改即可,ioc技术把对象new操作交给了spring,接触一定的接口和类实现的耦合化-->
<!--<bean id="userDao2" class="com.classes.UserDaoImpl2"></bean>-->
<bean id="userDao" class="com.classes.UserDaoImpl"></bean>
<bean id="UserService" class="com.classes.UserService">
<constructor-arg ref="userDao2"/>
</bean>
</beans>
通过这个xml配置文件,我们可以把申请UserDaoImpl的对象交给Spring,然后在修改的时候避免修改类中的函数和参数,只需要修改xml配置文件即可,比如:如果我们新建了一个UserDaoImpl2的类,然后这个类也实现了该接口,我们现在要在不改变类文件的情况下改为调用UserDaoImpl2的接口,我们可以直接在xml中把ref=“userDao”改为userDao2即可,这样我们就可以改为调用userDao2的接口了,实现解耦化。
5. 测试代码:
public void demo02() {
//先要创建Spring的工厂
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
// classpath就是类路径,src目录下的文件最终要编译到类路径下
UserService userDao = (UserService) applicationContext.getBean("UserService");
userDao.pp();
}
嘻嘻 今天的学习就到这里啦!