1. IoC 容器的概念
IoC 容器指 具有依赖注入功能的容器,IoC 容器负责实例化、定位、配置应用程序中的对象及建立这些对象间的依赖。应用程序无需直接在代码中 new 相关对象,而是由 IoC 容器进行组装。在Spring 中 BeanFactory 是 IoC 容器的实际代表者。
Spring IoC 容器通过读取配置文件中配置元数据,通过元数据对用中的各个对象进行实例化及装配。一般使用基于 xml 配置文件进行配置元数据,而且 spring 与 配置文件 完全解耦,可以使用其他方式进行配置元数据,比如 注解、基于 Java 文件的、基于属性文件的配置。。
2. Bean 的概念
由 IoC 容器管理的那些 对象称之为 Bean,Bean 就是由 Spring 容器初始化、装配及管理的对象,除此之外,bean 与应用程序中其他对象没有什么区别了。
3. 下面我们搭建一个项目来演示一下Spring IoC 的基本使用
(环境 JDK 1.7.0_79,Eclipse 以及 spring 4.2.2 release,注意:该版本spring 只支持 JDK 1.6+
(下载地址:http://repo.spring.io/release/org/springframework/spring/))
使用 Eclipse 新建 Java project,命名为 Spring_IOC,同时import spring的 jar 包。
User.java
public class User { private int userId; private String username;// 用户姓名 private String sex;// 性别 private Date birthday;// 出生日期 private String address;// 地址 private String detail;// 详细信息 private Float score;// 成绩 //getter() and setter()... }
UserService.java
public interface UserService { public void addUser(User user); }
UserServiceImpl.java
public class UserServiceImpl implements UserService { private UserDAO userDAO; public UserDAO getUserDAO() { return userDAO; } public void setUserDAO(UserDAO userDAO) { this.userDAO = userDAO; } @Override public void addUser(User user) { this.userDAO.saveUser(user); } }
UserDAO.java
public interface UserDAO { public void saveUser(User user); }
UserDAOImpl.java
public class UserDAOImpl implements UserDAO { @Override public void saveUser(User user) { System.out.println("save user to Database"); } }
UserServiceTest.java (Junit test case)
public class UserServiceTest { @Before public void setUp() throws Exception { } @Test public void testAddUser() throws Exception { ApplicationContext ctx = new ClassPathXmlApplicationContext("beans.xml"); UserServiceImpl service = (UserServiceImpl) ctx.getBean("userService"); User user = new User(); user.setUsername("Olive"); service.addUser(user); } }
Beans.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.xsd"> <bean id="userDAO" class="com.dao.impl.UserDAOImpl" /> <bean id="userService" class="com.service.impl.UserServiceImpl"> <property name="userDAO" ref="userDAO" /> </bean> </beans>
4. 注入方式
OK,Demo搭建起来了,下面讲一下 IoC 容器的几种注入方式:接口注入、构造方法、setter方法注入(前两者用的比较少)。
(1)构造方法注入:
首先,在依赖对象(UserServiceImpl)中构建显式的构造方法,构造方法包含 被依赖对象(UserDAOImpl)。在配置文件(beans.xml)中配置好 userDAOImpl 和 UserDAOImpl,如下:
在 UserServiceImpl 中添加构造方法:
//constructor public UserServiceImpl(UserDAO userDAO) { super(); this.userDAO = userDAO; }
修改配置文件:
<?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"> <bean id="userDAO" class="com.dao.impl.UserDAOImpl" /> <bean id="userService" class="com.service.impl.UserServiceImpl"> <!-- <property name="userDAO" ref="userDAO" /> --> <!-- constructor --> <constructor-arg> <ref bean="userDAO"/> </constructor-arg> </bean> </beans>
(2)setter 方法注入:
要求在依赖对象(UserServiceImpl)中提供被依赖对象(UserDAOImpl)的setter() 方法,then 在配置文件 <bean><property /></bean> property中配置被依赖对象。
public class UserServiceImpl implements UserService { private UserDAO userDAO; public UserDAO getUserDAO() { return userDAO; } public void setUserDAO(UserDAO userDAO) { this.userDAO = userDAO; } //constructor // public UserServiceImpl(UserDAO userDAO) { // super(); // this.userDAO = userDAO; // } @Override public void addUser(User user) { this.userDAO.saveUser(user); } }
<?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"> <bean id="userDAO" class="com.dao.impl.UserDAOImpl" /> <bean id="userService" class="com.service.impl.UserServiceImpl"> <property name="userDAO" ref="userDAO" /> <!-- constructor --> <!-- <constructor-arg> <ref bean="userDAO"/> </constructor-arg> --> </bean> </beans>
(3)接口注入:由于笔者自己也不太清楚,先暂时空着,待以后弄清楚后补充