Spring框架之BeanFactory和ApplicationContext的区别

从下图中可以看出BeanFactory是顶级接口而 ApplicationContext是它的子类。

1、BeanFactory

Spring容器顶层接口:获取Bean对象;管理类和类之间的关系(依赖关系)BeanFactory由org.springframework.beans.factory.BeanFactory接口定义 BeanFactory是工厂模式(Factory pattern)的实现,是IOC容器的核心接口,它的职责包括:实例化、定位、配置应用程序中的对象及建立这些对象间的依赖。

BeanFactory中的API

containsBean(String beanName) 判断工厂中是否包含给定名称的bean定义,若有则返回true。

Object  getBean(String  str) 返回给定名称注册的bean实例。根据bean的配置情况,
如果是singleton模
式将返回一个共享实例,否则将返回一个新建的实例,如果没有找到指定bean,该方法可能会抛出异常。

Object  getBean(String, Class) 返回以给定名称注册的bean实例,并转换为给定class类型

Class  getType(String name) 返回给定名称的bean的Class,如果没有找到指定的bean实例,则排除
NoSuchBeanDefinitionException异常

boolean  isSingleton(String) 判断给定名称的bean定义是否为单例模式      

String[]  getAliases(String name) 返回给定bean名称的所有别名

2、ApplicationContext接口

      ApplicationContext  是基于BeanFactory之上的,提供了应用程序框架服务,扩展的新功能如下:提供国际化的支持资源访问,如URL和文件 事件传递载入多个配置文件等 实现类常见有三个

ClassPathXmlApplicationContext:-classpath路径加载xml文件的

FileSystemXmlApplicationContext:基于项目根路径进行加载xml文件的

AnnotationConfigApplicationContext:基于注解的配置。基于类书写的配置。

BeanFactory和ApplicationContext区别:

1、BeanFactory 才是 Spring 容器中的顶层接口。
2、ApplicationContext 是它的子接口。
3、单例模式下创建对象的时间点不一样:
4、ApplicationContext:(饿汉模式 ClassPathXmlApplicationContext)只要一读取配置文件,马上就会创建配置文件中配置的对象。
5、BeanFactory:(懒汉模式 XmlBeanFactory)什么时候getBean("id"),也就是说当根据id获取对象时,才会创建。

3、实现通过IOC实例化对象

可以通过这些接口把实例化对象交给IOC容器来管理。下面展示如何实现这个过程。

首先在springmvc配置文件中,加入下面这句话让IOC容器能找到这个类并能调取它的构造方法,下面这种方式默认调用无参构造。

<bean id="userDao" class="com.aaa.UserDao"></bean>

<!--
默认单例
scope:常用  singleton,prototype

	singleton:单例的(默认值)当加载配置文件时,就会创建对象。

	prototype:多例的(当getBean时才会创建对象)

	request:作用于请求范围---同一个那么使用bean同一个。

	session:作用于会话范围---同一个会话

-->

然后我们来通过IOC容器创建对象

public class TestBeanFactoryAndApplication {
    public static void main(String[] args) {
        //该方式是当你需要构建对象时,才会去创建。并且是单例模式,共享对象。
        //读取配置文件
        ClassPathResource resource = new ClassPathResource("springmvc.xml");
        //解析配置文件
        XmlBeanFactory factory = new XmlBeanFactory(resource);
        //根据ID调用bean
        //获取bean的方式总共有三种
        //通过bean.xml文件中bean标签的id的值获取bean(使用默认构造方法)
        Object userDao = factory.getBean("userDao");
        //通过类型去获取 
        IUserDao userDao = app.getBean(IUserDao.class);  //通过类型获取bean对象。
        // 通过 id  +  类型去获取
        IUserDao userDao = app.getBean("userDao", IUserDao.class);
       
    }
}


 public static void main(String[] args) {
        //在加载spring容器时,spring会把配置文件中所有的bean创建好。
        ApplicationContext app=new ClassPathXmlApplicationContext("application.xml");
      
        //根据ID调用bean
        Object userDao = factory.getBean("userDao");
    }

4、配置有参构造

4.1、使用构造函数提供注入

如果使用构造函数注入,需要在bean.xml文件的bean标签中添加constructor-arg标签

标签中的属性:

  • ​ type : 用于指定要注入的数据的类型,该数据类型也是构造函数中某个或某些参数的类型。
  • ​ index: 用指定给构造函数中指定索引位置的参数赋值,索引从0开始。
  • ​ name: 用于给构造函数的参数赋值,指定参数的名称直接赋值 (常用)
  • ​ value : 用于提供基本类型和String类型的数据
  • ​ ref : 用于指定其它的bean类型数据,它指的就是在spring的IOC核心容器中出现过的bean

注意:在获取bean对象时,必须要注入数据,否则对象无法创建成功。

缺点:改变了bean对象的实例化方式,就算我们在创建对象时,用不到这些数据,也必须提供。

 <!--构造注入-->
    <bean id="p1" class="com.gzh.entity.Person">
        <constructor-arg name="age" value="18"></constructor-arg>
        <constructor-arg name="name" value="王五"></constructor-arg>
        <constructor-arg name="date" ref="d1"></constructor-arg>
    </bean>

    <!--日期对象的bean-->
    <bean id="d1" class="java.util.Date"></bean>

4.2、第二种:使用set方法注入(常用)

如果使用set函数注入,需要在bean.xml文件的bean标签中添加 property 标签

需要属性:

  • ​ name: 用于给无参空构造函数的参数赋值,指定设值的set方法(将set方法的set去掉把大写字母变小写 setAge()====>age)
  • ​ value : 用于提供基本类型和String类型的数据
  • ​ ref : 用于指定其它的bean类型数据,它指的就是在spring的IOC核心容器中出现过的bean

优点:解决了构造注入时的问题,可以选择性的注入值,不是必须注入全部了。  

	<!--注入java提供的Date类-->
    <bean id="date" class="java.util.Date"></bean>
    <!--set方法注入-->
    <bean id="person" class="com.gzh.entity.Person">
        <property name="name" value="王五"></property>
        <property name="age" value="29"></property>
        <property name="birthday" ref="date"></property>
    </bean>

4.3、第三种:使用注解提供 (注意开启注解的包扫描)

<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
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd">
	<!--开启注解包扫描-->
    <context:component-scan base-package="要扫描的包全名"></context:component-scan>
</beans>

注解分类

1.用于创建对象的:

​ 作用和在xml配置文件中编写一个< bean>标签实现的功能一样

@Component:(只要不属于三层架构 就使用)
	作用:用于把当前类对象存入spring容器中。
	具有value属性,用于指定bean的id,如果不写value,默认跟当前类名对应(首字母改小写)
	@Component("student1")作用就相当于:
	<bean id="id" class="全类名"></bean>

衍生三个注解:
@Controller(表现层)     @Service(业务层)      @Repository(持久层)
	这三个注解的作用和@Component注解一样,是spring框架为我们提供的明确的三层架构使用的注解,
让我们的三层架构更加清晰。

2.用于注入数据的:

@Autowired *****重点
作用:自动按照类型注入,只要容器中有唯一的一个bean对象类型和要注入的变量类型匹配,就可以注入成功。
    如果IOC容器中没有任何bean的类型和要注入的变量类型匹配,则报错
    如果IOC容器中有多个类型匹配时,会根据要注入的变量名作为id去匹配,如果匹配到了,就可以执行,
否则,报错。
注意:使用注解时,set方法就不是必要的了。
以上@Autowired注解存在一定的局限性,(如果核心容器中有多个相同对象,只使用@Autowired是无法注入
成功的)如何解决问题?

@Qualifier
	作用:在按照类型注入的基础上再按照名称注入。它再给类成员注入时不能单独使用。但是再给方法注入时可以。
	属性:value 用于指定注入的bean的id

@Resource
	作用:直接按照bean的id注入。它可以独立使用。
	属性:name   用于指定bean的id
以上三个注解都只能注入其它bean类型的数据,而基本类型和String类型无法使用上述注解。那么如何注入基本数据类型和String类型呢?(集合类型只能通过xml注入)

@Value
	作用:用于注入基本数据类型和String数据类型。

3.用于改变作用范围的

作用和bean标签中的scope属性的功能一样

@Scope:
    作用:用于指定bean的作用范围
    属性:value  指定范围的取值。常用  singleton  prototype

4.和生命周期相关的

作用和bean标签中的init-method和destory-method方法的作用一样

@PostConstruct:用于指定初始化方法
@PreDestroy      :用于指定销毁方法

注释配置

public class Person {
 
    private String name;
 
    private Integer age;
 
    // 无参构造器
    public Person() {
        System.out.println("xmlPerson NoConstructor");
    }
 
    //对象创建并赋值之后调用
	@PostConstruct
    public void init() {
        System.out.println("xmlPerson init-method");
    }
 
    // 充当destroy method
    // 销毁方法的注解方式 等同于destroy-method
    @PreDestroy
    public void destroy() {
        System.out.println("xmlPerson destroy-method");
    }
}

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">
 
	<!--配置Person对象创建-->
	<bean id="xmlPerson" class="com.best.entity.Person" init-method="init" destroy-
method="destroy">
	</bean>
</beans>

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值