ClassXmlAplicationContext和FileSystemXmlApplicationContext的区别      https://www.cnblogs.com/sxdcgaq8080/p/5650404.html

spring学习-ApplicationContext-spring上下文深入理解

1、SPring 容器

基于 Spring 的应用中,所有的对象(即bean)生存于 Spring 容器,Spring 负责创建、装配、配置并管理这些bean的整个生命周期。

一、Spring 容器

Spring 容器并不是只有一个实现,而是自带了多个容器实现,可归纳为两种不同类型:bean 工厂、应用上下文。

bean工厂:由 org.springframework.beans.factory.BeanFactory接口定义;

ApplicationContext:由 org.springframework.context.ApplicationContext接口定义。

两类别关系:ApplicationContext 基于 BeanFactory 构建,并提供应用框架级别的服务,即BeanFactory是基础,ApplicationContext是一个提升。

二、BeanFactory

基础接口定义:

public interface BeanFactory {
String FACTORY_BEAN_PREFIX = "&";
Object getBean(String name) throws BeansException;
<T> T getBean(String name, Class<T> requiredType) throws BeansException;
<T> T getBean(Class<T> requiredType) throws BeansException;
Object getBean(String name, Object... args) throws BeansException;
boolean containsBean(String name);
boolean isSingleton(String name) throws NoSuchBeanDefinitionException;
boolean isPrototype(String name) throws NoSuchBeanDefinitionException;
boolean isTypeMatch(String name, Class<?> targetType) throws NoSuchBeanDefinitionException;
Class<?> getType(String name) throws NoSuchBeanDefinitionException;
String[] getAliases(String name);
}

三、ApplicationContext

基础继承关系:

public interface ApplicationContext extends EnvironmentCapable, ListableBeanFactory, HierarchicalBeanFactory,
MessageSource, ApplicationEventPublisher, ResourcePatternResolver{...}
可见ApplicationContext是在BeanFactory基础上定义的,实际上ApplicationContext是BeanFactory的一个超全集。

/**
* ApplicationContext是一个为application提供配置信息的中心接口,当application运行时,它仅是可读的,但也可能重新加载,如果接口允许的 * 话。
* ApplicationContex提供了如下功能:
*
* 1、访问application的组件(即bean)的BeanFactory中的方法。继承于:org.springframework.beans.factory.ListableBeanFactory;
* 2、以常规方式加载文件资源的能力。继承于:org.springframework.core.io.ResourceLoader;
* 3、发布Event到注册过的listener的能力。继承于:ApplicationEventPublisher;
* 4、解决message的能力,即支持国际化。继承于:MessageSource;
* 从父上下文继承,在后代语境中的定义将永远优先。 这意味着,例如,一个单亲上下文可以由整个Web应用程序使用,而每个servlet都有它独立于任何其他servlet的子环境。(不明白)
* 除了标准的org.springframework.beans.factory.BeanFactory的生命周期的能力外,ApplicationContext实现检测和调用
* ApplicationContextAware bean 、ResourceLoaderAware bean
* 及ApplicationEventPublisherAware、MessageSourceAware bean。
*/

通过集成实现的接口就知道他具有spring里面经典的工厂方法,还有对国际化支持的Message,以及配置信息的Resource,还有spring支持的发布和监听事件功能。一个Context基本上把spring具有的核心功能都包裹起来了,那么这就是spring框架运行需要的环境,也就是常说的上下文。任何一个框架运行都通过一个类来进行描述它执行时的环境,ServletContext也是一样,就是Servlet环境信息。可以将context理解为一个框架执行信息的载体,可以理解问一个框架的门面(门面模式),将框架内部的各个组件信息都通过一个context暴露给外部。

所以Application 比BeanFactory多了3项能力:加载资源文件能力、发布事件能力、国际化能力。看第四点中示例!

关于Aware 接口的基础,查看另外一篇日志:

四、ApplicationContext增强能力

第三点列了ApplicationContext 增加的3项能力,现分别举基础例子。

1、资源加载:ResourceLoader接口

ResourceLoader接口定义:

public interface ResourceLoader {

    /** 从class path 路径加载时的伪资源URL: "classpath:" 。不陌生,web.xml配置中指定类路径下资源时便要加此前缀*/
String CLASSPATH_URL_PREFIX = ResourceUtils.CLASSPATH_URL_PREFIX; /**返回指定path的资源*/
Resource getResource(String location); /**需要直接访问ClassLoader的客户端可以这样做,即以与ResourceLoader统一的方式,而不是依赖线程上下文ClassLoader*/
ClassLoader getClassLoader();
}

说明:

Resource 也是一个接口,定义如下:

public interface Resource extends InputStreamSource {

/**说明:InputStreamSource接口中只有一个方法:InputStream getInputStream()。可见Resource本质上是一个输入流,只是丰富了方法。*/
boolean exists();
boolean isReadable();
boolean isOpen();
URL getURL() throws IOException;
URI getURI() throws IOException;
File getFile() throws IOException; //常用方法
long contentLength() throws IOException;
long lastModified() throws IOException;
Resource createRelative(String relativePath) throws IOException;
String getFilename();
String getDescription();
}

问题:
已经可以通过ResourceLoader 返回Resource 对象得到我们需要的文件了,那ResourceLoader 中getClassLoader方法有什么作用?

答:ClassLoader是java.lang包中的类,用于JVM 加载class文件,这些class文件也是广义上的资源。在ResourceLoader 中定义方法得到此类的目的应该是application运行时并不是一下子把应用所涉及的class文件都加载,而是先加载核心的,再加载我们自己写的代码生成的类,且是用到时再加载。ClassLoader 保存了加载某个class文件时所用的位置(可能是本地,也可能是网络服务器上),所以在一个已加载的A.class文件中涉及到另一个B.class的对象时,便可以通过getClassLoader 从加载A.class的资源路径中加载B.class,之后生成对象,因为A.class与B.class在web系统中都是是位于服务器上的。简言之,两个class对应了两个java文件,A.java中使用了B.java中的类,则程序执行到A.class时,A.class从哪加载的,B.class也从那加载(或许还会自动扫描那台主机上ClassPath的所有目录,以找到B.class)。

<p> Normally, the Java virtual machine loads classes from the local file
* system in a platform-dependent manner. For example, on UNIX systems, the
* virtual machine loads classes from the directory defined by the
* <tt>CLASSPATH</tt> environment variable.
*
* <p> However, some classes may not originate from a file; they may originate
* from other sources, such as the network, or they could be constructed by an
* application. The method {@link #defineClass(String, byte[], int, int)
* <tt>defineClass</tt>} converts an array of bytes into an instance of class
* <tt>Class</tt>. Instances of this newly defined class can be created using
* {@link Class#newInstance <tt>Class.newInstance</tt>}.

ResourceLoader示例:

ApplicationContext继承了ResourceLoader接口,所以可以直接获取文件。

ApplicationContext appCtx=FileSystemXMLApplication("applicationContext.xml");
Resource reSrc=appCtx.getResource("sourceURL");
//使用Resource对象获取文件
File file=reSrc.getFile();
注:sourceURL可以是"classpath:"开头的类路径,也可是"WEB-INF/src/"开头的路径,更可以是绝对路径。

2、事件发布:ApplicationEvent类、ApplicationListener接口、ApplicationContextAware接口

步骤:

(1)、写一个事件类,继承ApplicationEvent 类。如:

class SayHello enxtends ApplicationEvent{
public SayHello(){super();}
}

(2)、写一个ApplicationEvent 事件监听类,实现 ApplicationListener接口。如:

class SayListener implement ApplicationListener{
public void onApplicationEvent(ApplicationEvent ev){
if(ev instanceof SayHello){
System.out.println("收到SayHello事件");
}
}
}

(3)、写一个事件发布管理类,实现ApplicationContextAware 接口。如:

public class ManagerEvent implements ApplicationContextAware{
private ApplicationContext appCtx=null;
@Override
public void setApplicationContext(ApplicationContext applicationContext)
throws BeansException {
appCtx=applicationContext;
}
public void publish(ApplicationEvent event){/*此处运用了控制翻转的思想,即传入ApplicationEvent的子类,因为是类的继承而非接口的实现,所以在SayHello类中并没有添加实际的方法,只是用于区分事件而已*/
if(event!=null)
appCtx.publisherEvent(event);
}
}

(3)、配置Spring 容器中的bean,可通过XML 配置,如:WEB-INF/src下的myConfig.xml:省略了xml声明部门

<beans>
<bean id="hellowEvent" class="myPackageName.SayHello"/>
<bean id="manageEvent" class="myPackage.ManageEvent"/>
<bean id="listerner" class="myPackage.SayListener"/>
</beans>

(4)、测试:主函数部分代码:

public static void main(String[] args){
ApplicationContext appCtx=new FileSystemApplicationContext("WEB-INF/src/myConfig.xml");
SayHello event=appCtx.getBean("hellowEvent");
ManageEvent manage=appCtx.getBean("manageEvent");
manage.publish(event);//发布事件
}

说明:

Spring 所有bean位于一个容器中,即ApplicationContext或BeanFactory中,所以所有的操作都是依赖于这个容器,容器定义后,不能重新定义,只能通过refresh方法(有待补充)。如果某个bean中本身要使用容器的某个功能,应该实现ApplicationContextAware 接口,获得ApplicationContext的句柄,对其它***Aware方法同理。

3、国际化:MessageResource接口

见另一边日志:http://blog.csdn.net/qq_19865749/article/details/70195063

五、几个常用ApplicationContext

使用Spring 的基础是通过XML等形式定义一些JavaBean,之后使用Spring 的BeanFactory 或ApplicationContext 创建并管理这些JavaBean,常用的几个ApplicationContext :

1、FileSystemXmlApplicationContext:

从文件系统下的一个或多个XML 配置文件加载上下文定义。

示例:

ApplicationContext appCtx=new FileSystemXmlApplicationContext(new String[]{"WebContent/WEB-INF/applicationContext.xml","WebContent/WEB-INF/config.xml"});//以String数组形式传入多个xml文件路径

说明:

查找路径默认为工程文件夹下,所以若XML文件不是直接处于工程文件夹下,则应把路径写上,如上面的 WebContent/WEB-INF/。也可用绝对路径。

2、ClassPathXMLApplicationContext:

从类路径下的一个或多个XML 配置文件加载上下文定义。

示例:

ApplicationContext appCtx=new ClassPathXmlApplicationContext("applicationContext.xml");
说明:
查找路径默认为src下,所以同上,若XML 文件不是直接属于src文件夹下,则应该加上路径,如:xml文件放在com.milan.pojo包下,则应为:
ApplicationContext appCtx=new ClassPathXmlApplicationContext("com/milan/pojo/applicationContext.xml");

3、XmlWebApplicationContext:

从Web 应用下的一个或多个XML 配置文件中加载上下文定义。

spring基础学习的更多相关文章

  1. spring基础学习01

    spring基础 Spring是一个开放源代码的设计层面框架,他解决的是业务逻辑层和其他各层的松耦合问题,因此它将面向接口的编程思想贯穿整个系统应用 IOC控制反转 把创建对象和维护对象之间的关系权利 ...

  2. Spring基础学习(四)—AOP

    一.AOP基础 1.基本需求      需求: 日志功能,在程序执行期间记录发生的活动. ArithmeticCalculate.java public interface ArithmeticCal ...

  3. Spring基础学习(一)—初识Spring

    一.Spring的使用 1.导入jar包 2.编写实体类 Person.java public class Person{ private String name; public void say() ...

  4. Spring基础学习,附例子代码讲解

    什么是Spring.IOC.AOP.DI?     Spring是一个基于IOC和AOP的结构J2EE系统的框架.     IOC(Inversion Of Control)控制反转(Spring的基 ...

  5. 使用JavaConfig方式-Spring 基础学习

    在Spring的使用中,大量采用xml方式配置类之间的关系太过于繁琐(个人这么认为),而在学习了Spring4后发下使用JavaConfig方式来配置这些关系会更加的简单明了. 测试环境 1. Apa ...

  6. Spring基础学习笔记

    1. Spring入门 1. 1 Spring的体系结构 1.2 HelloWorld 1.2.1 Maven的使用 1)maven 的javase工程目录结构: 2)maven的settings.x ...

  7. Spring基础学习笔记-Bean的基础知识

    一. Bean的定义,初始化,使用和销毁 二.ref指定依赖的三种模式 三.Bean的五种自动装配模式(autowire) 四.Bean依赖检查的4种模式:配合atuowire使用,dependenc ...

  8. Spring基础学习(五)—事务管理

    一.事务基本认识 1.事务的概述      为了保证数据库中数据的一致性,数据的操作应当是离散的成组的逻辑单元.当它全部完成时,数据的一致性可以保持,而当这个单元中的一部分操作失败,整个事务应当全部视 ...

  9. Spring基础学习(三)—详解Bean(下)

    一.Bean的生命周期 1.概述      Spring IOC容器可以管理Bean的生命周期,Spring 允许在Bean的生命周期的特定点执行定制的任务.      Spring IOC容器对Be ...

随机推荐

  1. 快速了解前端开发HTML的正确姿势

    摘要:web前端开发(也称为客户端开发)主要是通过html,CSS和JavaScript等前端技术,实现网站在客服端的正确显示及交互功能. 一.web标准介绍 web标准: w3c:万维网联盟组织,用 ...

  2. solr综合案例

    1.  综合案例 1.1. 需求 使用Solr实现电商网站中商品信息搜索功能,可以根据关键字.分类.价格搜索商品信息,也可以根据价格进行排序,并且实现分页功能. 界面如下: 1.2分析 开发人员需要的 ...

  3. 单元测试框架怎么搭?快来看看新版Junit5的这些神奇之处吧!

    为什么使用JUnit5 JUnit4被广泛使用,但是许多场景下使用起来语法较为繁琐,JUnit5中支持lambda表达式,语法简单且代码不冗余. JUnit5易扩展,包容性强,可以接入其他的测试引擎. ...

  4. Python-为元组中每个元素命名

    学生信息系统: (名字,年龄,性别,邮箱地址) 为了减少存储开支,每个学生的信息都以一个元组形式存放 如: ('tom', 18,'male','tom@qq.com' ) ('jom', 18,'m ...

  5. Nginx+Gunicorn+Supervisor部署Flask应用

    Flask 内置了简单的 Web 环境,让我们在开发的时候只需要专注于应用实现,而真正要在生产环境运行时这个简单的 Web 环境就不够用了,还需要一系列操作才能让 Web 应用高效的运行起来.现在记录 ...

  6. 001 01 Android 零基础入门 01 Java基础语法 01 Java初识 01 导学

    001 01 Android 零基础入门 01 Java基础语法 01 Java初识 01 导学 welcome to Java World 欢迎来到Java世界 一起领略Java编程世界的奥秘与奥妙 ...

  7. C/C++ 中 exit() 函数

    参考: https://blog.csdn.net/jjjcainiao/article/details/21935795 知乎上的问题]C/C++ 中 exit() 函数的参数到底有什么意义? C ...

  8. Python自学02day——变量和简单的数据类型

    1.变量是什么? 变量存储在内存中的值,这就意味着在创建变量时会在内存中开辟一个空间. 基于变量的数据类型,解释器会分配指定内存,并决定什么数据可以被存储在内存中. 因此,变量可以指定不同的数据类型, ...

  9. Linux init 详解(0,1,2,3,4,5,6)

    一.什么是 init init是Linux系统操作中不可缺少的程序之一. 所谓的init进程,它是一个由内核启动的用户级进程. 内核自行启动(已经被载入内存,开始运行,并已初始化所有的设备驱动程序和数 ...

  10. 云原生 go-zero 微服务框架

    0. go-zero介绍 go-zero是一个集成了各种工程实践的web和rpc框架.通过弹性设计保障了大并发服务端的稳定性,经受了充分的实战检验. go-zero包含极简的API定义和生成工具goc ...