上一篇的HelloWorld简单实现了用AC容器(也就是IOC容器)来创建UserDao类。IOC和DI说的是一回事,只不过一个从宏观上描述 ,一个从细节上描述。IOC是一种将组件依赖关系的创建和管理置于程序外部的技术。这使得一个类是很独立的,不需要承担更多的责任。
Spring创建对象是在我们把这个对象类已经建好,并且按照这个类的结构,在ApplicationContext.xml中安排好。然后通过配置文件反射创建这个类的对象,并且协调管理对象和对象之间的关系!!
IOC容器帮我们完成了两件事
1.对象的创建
2.对象关系的建立(DI依赖注入)
在IOC中对象的创建分三种创建方式,注入也有三种方式
一
IOC中对象的创建
1.无参构造方式创建对象,就像HelloWorld实例中一样,只是简单的通过beans.xml反射出对象
2.有参构造方式创建对象,意思是说这个对象是有参数的,那么在通过beans.xml反射的时候,还需要描述这个bean(对象)的参数,实例如下
实际的对象UserDao
public class UserDao{
private Integer abc;
private String ccc;
private boolean aa;
public UserDao(Integer abc,String ccc,boolean aa){//这个bean对象的带参构造器
super();
this.abc = abc;
this.ccc = ccc;
this.aa = aa;
System.out.println("IOC容器创建有参数的UserDao时,我将被初始化");
}
public UsreDao(){//这个bean对象的无参构造
System.out.println("IOC容器创建无参数的UserDao时,我会被初始化");
}
public void add(){
System.out.println("add.......");
}
}
beans.xml中做如下添加
<bean id="userDao" class="com.bjsxt.dao.UserDao">
<constructor-arg index="0" values="123" ></constructor-arg> //constructor-arg说明这个bean带参数,多个参数由index来区别是第几个
<constructor-arg index=“1” values="xiaogao"></constructor-arg> //values是具体注入的值
<constructor-arg index="2" values="true"></constructor-arg> //第三个值是boolean型的
</bean>
写一个Test方法来测试一下有没有初始化有参构造器
public class Test{
public static void main(String[ ] args){
ApplicationContext ac = new ClassPathXmlApplicationContext(
new String[]{ "beans.xml"}
);
UserDao dao = (UserDao)ac.getBean("userDao");
dao.add();
}
}
3.工厂方式创建对象,IOC容器中的工厂是在beans.xml中把daoFactory反射出来,再由daoFactory来创建对象,而不是由容器来创建对象,这是因为有些时候,别人已经写 好了daoFactory,你不便再修改(人家通过daoFactory创建了不少对象,你难道再一一通过IOC创建出来吗,肯定没必要),所以要直接把daoFactory反射出来,让它以前怎么创建还怎么创建。
工厂方式创建对象的实例
在beans.xml中重新定义一个bean,如下
<bean id="daoFactory" class="com.bjsxt.dao.DaoFactory"></bean> //把别人写好的daoFactory反射出来
<bean id="teacherDao" factory-bean="daoFactory" factory-method="newInstance"></bean> //factory-bean写上面工厂bean的ID,说明这个bean是工厂new出来的,factory-method写daoFactory new出teacherDao后执行teacherDao中的哪个方法
别人写好的对象和工厂
public class TeacherDao{
public void add(){
System.out.println("teacher ..... add.....");
}
}
public class DaoFactory{
public TeacherDao newInstance(){
return new TeacherDao();
}
}
然后在Test.java中稍作改动
public class Test{
public static void main(String[ ] args ){
ApplicationContext ac = new ClassPathXmlApplicationContext(
new String[ ] {"beans.xml"}
);
TeacherDao dao = (TeacherDao) ac.getBean("teacherDao"); //这里不需要得到配置文件里的daoFactory,那只是告诉IOC容器daoFactory和TeacherDao的关系
dao.add();
}
}
——————IOC容器帮我们创建对象的三种方式end——————————————
二
IOC容器对象关系的建立方式(也就是注入方式)
1.setter注入(最常见)
建立一个action包,下面建立一个UserAction.java
public class UserAction{
private UserDao userDao;
public UserDao getUserDao(){
return userDao;
}
public void setUserDao(UserDao userDao){
this.userDao = userDao;
}
public String add(){
userDao.add();//这个userDao就是private UserDao userDao的那个,只要有set、get方法,这样就可以用了,不需要new,因为在beans.xml中已经分配好了userAction和userDao的关系,具体体现在这句:ref="userDao",struts2中也有这个功能。
return null;
}
}
UserDao.java
public class UserDao {
public void add(){
System.out.println("UserDao.add(add........)");
}
}
在beans.xml中加入两个bean(spring的配置文件叫ApplicationContext.xml最正宗,这里简写成beans.xml)
<bean id="userAction" class="com.bjsxt.action.UserAction">//反射出userAction
<property name="userDao" ref="userDao"></property>//这里是通过userDao找到userAction中的setUserDao(UserDao userDao)方法; 就是简单的set注入,默认调用set方法,在action中写上set方法就成了 。property就是userAction类中的参数的意思
</bean>
<bean id="userDao" class="com.bjsxt.dao.UserDao"></bean>//这个bean一定别丢,不然找不到userDao的对象会报错
Test.java
public class Test {
public static void main(String[] args) {
ApplicationContext ac = new ClassPathXmlApplicationContext(
new String[]{"ApplicationContext.xml"}
);
UserAction userAction = (UserAction) ac.getBean("userAction");
userAction.add();
}
}
2.构造器注入(和set注入不同的是不用创建set、get方法了,改创建构造器了,然后beans.xml配置文件中再改改写法,就这么简单)
public class UserAction{
private UserDao userDao;
public UserAction(UserDao userDao){//建了个有参构造
super();
this.userDao = userDao;
}
public String add(){
userDao.add();
return null;
}
}
在beans.xml中添加两个bean
<bean id="userAction" class="com.bjsxt.action.UserAction">
<constructor-arg index="0" ref="userDao"></constructor-arg>
</bean>
<bean id="userDao" class="com.bjsxt.dao.UserDao"></bean>
Test.java中写
public class Test{
public static void main(String[ ] args){
ApplicationContext ac = new ClassPathXmlApplicationContext(
new String[ ] {"beans.xml"}
);
UserAction userAction = (UserAction)ac.getBean("userAction");
userAction.add();
}
}
重要提示:Spring环境下,服务类千万不要自己new,要从容器当中拿!!!!因为容器中的对象不单单是对象,还包含和其它对象的关系。Spring约束编程,改变一种编程习惯。
3.接口注入(了解)
Spring中的beans.xml也可以叫ApplicationContext.xml,这个是最规范的叫法,叫这名字,配置文件图标会变成小树叶。
———————————对象关系的建立(注入的建立)end———————————————————————