Spring容器创建Bean的三种方式
我们知道,Spring是通过IOC容器实现对对象(也就是Bean)的管理的。IOC容器通过读取配置元数据来获得要实例化、配置、组装对象的元信息,以便实现针对用户程序中对象的统一管理。

IOC容器可以使用的元数据配置信息有三种,分别是基于XML的配置、基于注解的配置和基于Java的配置,下面分别对三种配置进行介绍。
一、基于XML的容器配置
- 新建由IOC容器管理的实体类UserService
package com.bx.spring.service;
public class UserService {
public void print() {
System.out.println("UserService......");
}
}
- resources目录下新建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 id="userService" class="com.bx.spring.service.UserService"></bean>
</beans>
- 获取userService对象
package com.bx.spring;
import com.bx.spring.service.UserService;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Main {
public static void main(String[] args) {
//扫描路径
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml");
//获取bean
UserService userService = (UserService) context.getBean("userService");
userService.print();
}
}
二、基于注解的容器配置
- 新建被注入的类Person以及待注入的类Company
package com.bx.spring.eneity;
public class Person {
private String name = "bob";
private int age = 18;
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
package com.bx.spring.eneity;
import org.springframework.beans.factory.annotation.Autowired;
public class Company {
private Person person;
public Person getPerson() {
return person;
}
//使用@Autowired注解将person注入company中
@Autowired
public Company(Person person) {
this.person = person;
}
}
- 在resources目录下新建applicationContext2.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"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd">
<!-- 注解配置启用-->
<context:annotation-config/>
<bean id="person" class="com.bx.spring.eneity.Person">
</bean>
<bean id="company" class="com.bx.spring.eneity.Company">
</bean>
</beans>
- 运行主类,获取company实体
package com.bx.spring;
import com.bx.spring.eneity.Company;
import org.springframework.context.support.ClassPathXmlApplicationContext;
public class Main {
public static void main(String[] args) {
//扫描路径
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("applicationContext2.xml");
//获取bean
Company company = (Company) context.getBean("company");
System.out.println(company.getPerson().toString());
}
}
以上采用注解注入依赖的方式仍然需要在xml配置文件中通过<bean>标签定义bean的元信息。实际上,可以进一步对xml进行简化,可以通过以下两步骤进行简化。
- 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"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
https://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
https://www.springframework.org/schema/context/spring-context.xsd">
<!-- 注解配置启用-->
<context:annotation-config/>
<!--配置包扫描的路径,不再需要下面复杂的bean定义-->
<context:component-scan base-package="com.bx.spring"></context:component-scan>
<!-- <bean id="person" class="com.bx.spring.eneity.Person">-->
<!-- </bean>-->
<!-- <bean id="company" class="com.bx.spring.eneity.Company">-->
<!-- </bean>-->
</beans>
- 通过注解标记类为bean
package com.bx.spring.eneity;
import org.springframework.stereotype.Component;
@Component
public class Person {
private String name = "bob";
private int age = 18;
@Override
public String toString() {
return "Person{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
package com.bx.spring.eneity;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
@Component
public class Company {
private Person person;
public Person getPerson() {
return person;
}
@Autowired
public Company(Person person) {
this.person = person;
}
}
@Component注解告诉Spring这些类是需要注入的,前提是在xml中配置了包扫描路径。@Autowired注解将Person依赖注入到Company中。
三、基于Java类的容器配置
基于Java类的容器配置,无需XML配置文件,因而显得更加简洁。通常用@Configuration来注解一个类,表明它作为Bean定义的来源,可以理解为<beans>标签;用@Bean注解对Bean进行定义,可以理解为<bean>标签。
- 新建包config,包下新建配置类AppConfig。
//AppConfig.java
package com.bx.spring.config;
import com.bx.spring.service.UserService;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class AppConfig {
@Bean
public UserService myService() {
return new UserService();
}
}
//UserService.java
package com.bx.spring.service;
public class UserService {
public void print() {
System.out.println("UserService......");
}
}
2.运行主类
package com.bx.spring;
import com.bx.spring.config.AppConfig;
import com.bx.spring.service.UserService;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
public class Main {
public static void main(String[] args) {
//扫描路径
ApplicationContext context = new AnnotationConfigApplicationContext(AppConfig.class);
//获取bean
UserService userService = (UserService) context.getBean(UserService.class);
System.out.println(userService);
}
}
参考文档:
https://springdoc.cn/spring/core.html#beans-autowired-annotation
https://juejin.cn/post/7058885685851193380

浙公网安备 33010602011771号