1. 在IOC容器里配置Bean
这是上一篇文章中,配置Bean的代码。以及HelloWorld和Main两个类
<?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 -->
<bean id="helloworld" class="com.spring.beans.HelloWorld"> <!-- class是bean的类名 -->
<property name="name" value="Spring"></property>
</bean>
</beans>
package com.spring.beans;
public class HelloWorld {
private String name;
public void setName(String name) {
System.out.print("setName:" + name);
this.name = name;
}
public void hello() {
System.out.println("hello:" + name);
}
public HelloWorld() {
System.out.println("HelloWorld's Constructing..... ");
}
}
package com.spring.beans;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Main {
public static void main(String[] args) {
//1.创建HellowWorld的一个对象
//HelloWorld helloWorld = new HelloWorld();
//2.为name属性赋值
//helloWorld.setName("world");
//1.创建Spring的IOC容器对象
ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
//2.从IOC容器中获取Bean实例
HelloWorld helloWorld = (HelloWorld) ctx.getBean("helloworld");
//3.调用hello方法
helloWorld.hello();
}
}
1.1 bean节点介绍
我们在xml文件中通过bean节点来配置bean:
id:Bean的名称,标识容器中的bean
- 在IOC容器中必须是唯一的
- 若id没有指定,Spring自动将权限定性类名作为Bean的名字
- id可以指定多个名字,名字直接可用逗号,分号或者空格分隔
class:是一个全类名,通过反射的方法在IOC容器中创建Bean的实例。所以要求在Bean中有一个无参数的构造器(即HelloWorld类中的public HelloWorld() 这个方法),如果没有无参的构造器,运行时就会提示“No default constructor found”
1.2 IOC实例化
在IOC容器读取Bean配置创建Bean实例之前,必须对它进行实例化,只有在容器实例化之后,才可以从IOC容器里获取Bean实例并使用:
Spring提供了两种类型的IOC容器实现:
- BeanFactory:IOC容器的基本实现
- ApplicationContext:提供了更多的高级特性,是BeanFactory的子接口
BeanFactory是Spring框架的基础设施,面向Spring本身;而ApplicationContext面向使用Spring框架的开发者,几乎所有的应用场合都直接使用ApplicationContext而非底层的BeanFactory。(无论使用何种方式,配置文件是相同的)在Main类中就是使用“ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");”这句来实例化IOC容器。
1.3 ApplicationContext接口
ClassPathXmlApplicationContext是ApplicationContext接口的实现类,该实现类从类路径下加载配置文件
ApplicationContext接口还有一个实现类叫做FileSystemXmlApplicationContext,该实现类从文件系统中加载配置文件
1.4 从IOC容器中获取Bean实例
实现方法有两种:
- 利用id定位到IOC容器中的bean;Main类中的“HelloWorld helloWorld = (HelloWorld) ctx.getBean("helloworld");”这行代码就是利用id定位
- 利用类型返回IOC容器中的Bean,但要求IOC容器中必须只能有一个该类型的Bean
2. 依赖注入
Spring支持三种依赖注入的方式:
- 属性注入
- 构造器注入
- 工厂方法注入(很少使用,不推荐)
2.1 属性注入
属性注入即通过setter方法注入Bean的属性值或依赖的对象
属性注入使用<property>元素,使用name属性指定Bean的属性名称,value属性或<value>子节点指定属性值
applicationContext.xml文件中的“<property name="name" value="Spring"></property>”这句话就是属性注入
2.2 构造方法注入
通过构造方法注入Bean的属性值或依赖的对象,它保证了Bean实例在实例化后就可以使用
构造器注入在<constructor-arg>元素里声明属性,<constructor-arg>中没有name属性:
构造方法注入在后面的代码中有给到。
3. 代码及相应注释:
3.1 applicationContext.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
class:是一个全类名,通过反射的方法在IOC容器中创建Bean的实例。所以要求在Bean中有一个无参数的构造器
id:Bean的名称,标识容器中的bean,id唯一
-->
<bean id="helloworld" class="com.spring.beans.HelloWorld"> <!-- class是bean的类名 -->
<property name="name" value="Spring"></property>
</bean>
<!-- 通过构造方法来配置bean的属性 -->
<bean id="car" class="com.spring.beans.Car">
<constructor-arg value="Audi" index="0"></constructor-arg>
<constructor-arg value="AShanghai" index="1"></constructor-arg>
<constructor-arg value="3000" type="int"></constructor-arg>
</bean>
<!-- 使用构造器注入属性值可以指定参数的位置和参数的类型!以区分重载的构造器 -->
<bean id="car2" class="com.spring.beans.Car">
<constructor-arg value="Audi" type="java.lang.String"></constructor-arg>
<constructor-arg value="AShanghai" type="java.lang.String"></constructor-arg>
<constructor-arg value="200" type="double"></constructor-arg>
</bean>
</beans>
3.2 HelloWorld.java
package com.spring.beans;
public class HelloWorld {
private String name;
public void setName(String name) {
System.out.print("setName:" + name);
this.name = name;
}
public void hello() {
System.out.println("hello:" + name);
}
public HelloWorld() {
System.out.println("HelloWorld's Constructing..... ");
}
}
3.3 Car.java
package com.spring.beans;
public class Car {
private String brand;
private String corp;
private int price;
private double maxSpeed;
public Car(String brand, String corp, int price) {
super();
this.brand = brand;
this.corp = corp;
this.price = price;
}
public Car(String brand, String corp, double maxSpeed) {
super();
this.brand = brand;
this.corp = corp;
this.maxSpeed = maxSpeed;
}
@Override
public String toString() {
return "Car [brand=" + brand + ", corp=" + corp + ", price=" + price + ", maxSpeed=" + maxSpeed + "]";
}
}
3.4 Main.java
package com.spring.beans;
import java.io.File;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;
public class Main {
public static void main(String[] args) {
//1.创建HellowWorld的一个对象
//HelloWorld helloWorld = new HelloWorld();
//2.为name属性赋值
//helloWorld.setName("world");
//1.创建Spring的IOC容器对象
//ApplicationContext代表IOC容器
//ClassPathXmlApplicationContext是ApplicationContext接口的实现类,该实现类从类路径下加载配置文件
//ApplicationContext接口还有一个实现类叫做FileSystemXmlApplicationContext,该实现类从文件系统中加载配置文件
ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
//2.从IOC容器中获取Bean实例
//
//HelloWorld helloWorld = ctx.getBean(HelloWorld.class); //利用类型返回IOC容器中的Bean,但要求IOC容器中必须只能有一个该类型的Bean
HelloWorld helloWorld = (HelloWorld) ctx.getBean("helloworld"); //利用id定位到IOC容器中的bean
//3.调用hello方法
helloWorld.hello();
Car car = (Car) ctx.getBean("car");
System.out.println(car);
Car car2 = (Car) ctx.getBean("car2");
System.out.println(car2);
}
}