Spring 框架的概述以及Spring中基于XML的IOC配置
Spring 框架的概述以及Spring中基于XML的IOC配置
一、简介
- Spring的两大核心:IOC(DI)与AOP,IOC是反转控制,DI依赖注入
- 特点:轻量级、依赖注入、面向切面编程、容器、框架、一站式
- 优势:
- 方便解耦:做到编译期不依赖,运行期才依赖
- AOP的支持
- 声明式事务的支持
- 方便程序的测试
- 方便整合各种框架
- 降低JavaEE API的使用难度
- Spring源码很厉害
解耦:
耦合包括:类之间的和方法之间的
解决的思路:
- 在创建对象的时候用反射来创建,而不是new
- 读取配置文件来获取要创建的对象全限定类名
Bean:在计算机英语中有可重用组件的含义
javabean(用java语言编写的可重用组件)>实体类
二、工厂类解耦
在类中直接new的方法,耦合性太过于高,那么不如将这件事情交给一个工厂类来解决。
以下,我们将为所有的Bean创建一个工厂类,BeanFactory。
/**
* Bean:可重用组件
*/
public class BeanFactory {
private static Properties props;
//静态代码块
static{
try {
//1.实例化Properties对象
props=new Properties();
//2.获取Properties文件的流对象
InputStream in = BeanFactory.class.getClassLoader().getResourceAsStream("bean.properties");
props.load(in);
}
catch (Exception e){
throw new ExceptionInInitializerError("初始化properties失败");
}
}
}
BeanFactory初始化时,将从配置文件bean.properties中,获取Properties元素。
接下来实现getBean方法,根据Properties方法获取组件路径,并创建对象。
/**
* 根据bean的名称获取bean对象
* @param beanName
* @return
*/
public static Object getBean(String beanName){
Object bean = null;
try {
String beanPath = props.getProperty(beanName);
bean = Class.forName(beanPath).newInstance();
}catch (Exception e){
e.printStackTrace();
}
return bean;
}
以后就可以使用BeanFactory的类方法进行对象创建。
// IAccountDao accountDao=new AccountDaoImpl();
IAccountDao accountDao = (IAccountDao) BeanFactory.getBean("accountDao");
三、单例模式
然后有一个问题是:每次调用getBean方法,我们都会创建一个BeanFactory对象,这里完全可以替换成单例模式。
在BeanFactory中定义一个Map容器,存放我们需要创建的对象
private static Map<String,Object> beans;
接下来这样修改就能得到单例效果。
/**
* Bean:可重用组件
*/
public class BeanFactory {
private static Properties props;
//容器
private static Map<String,Object> beans;
//静态代码块
static{
try {
//1.实例化Properties对象
props=new Properties();
//2.获取Properties文件的流对象
InputStream in = BeanFactory.class.getClassLoader().getResourceAsStream("bean.properties");
props.load(in);
//3.容器实例化
beans = new HashMap<String, Object>();
//4.从配置文件中取出所有的key
Enumeration<String> keys = (Enumeration)props.keys();
//5.遍历枚举
while(keys.hasMoreElements()){
//取出每个key
String key = keys.nextElement();
//根据key获取value
String beanPath = props.getProperty(key);
Object value = Class.forName(beanPath);
//存放容器
beans.put(key,value);
}
}
catch (Exception e){
throw new ExceptionInInitializerError("初始化properties失败");
}
}
/**
* 根据bean的名称获取bean对象
* @param beanName
* @return
*/
// public static Object getBean(String beanName){
// Object bean = null;
//
// try {
// String beanPath = props.getProperty(beanName);
// bean = Class.forName(beanPath).newInstance();
// }catch (Exception e){
// e.printStackTrace();
// }
//
// return bean;
// }
public static Object getBean(String beanName){
return beans.get(beanName);
}
}
四、IOC(反转控制 Inversion of Control)
// IAccountService accountService=new AccountServiceImpl();
IAccountService accountService = (IAccountService) BeanFactory.getBean("accountService");
这两行代码的区别很能体现出IOC的思想。
区别:
- 一般情况:App直接向各种资源进行请求
- IOC:App向工厂进行请求,工厂与资源进行联系,工厂控制资源。
五、Spring中的IOC
以上是我们自己实现的IOC,这一切如果使用Spring的话,它将帮我们解决,所以我们学会了IOC的原理,接下来学Spring的用法。
删除掉上面的BeanFactory,这个由Spring来做。
- 在pom.xml中导入spring
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.0.2.RELEASE</version>
</dependency>
- 在resources下创建beans.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
https://www.springframework.org/schema/beans/spring-beans.xsd">
</beans>
创建bean:(bean标签的tag ”id“写bean的名字,”class“写bean的全限定类名)
<bean id="accountDao" class="com.mmj.dao.impl.AccountDaoImpl"></bean>
<bean id="accoutService" class="com.mmj.service.impl.AccountServiceImpl"></bean>
- 初始化容器
ApplicationContext context = new ClassPathXmlApplicationContext("services.xml", "daos.xml");
note:要用Spring的5.0.2版本,其他版本代码不太一样。
public class Client {
/**
* 获取Spring的ioc。根据id获取对象
* @param args
*/
public static void main(String[] args) {
// IAccountService accountService=new AccountServiceImpl();
//1. 获取核心容器对象
ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
IAccountService accountService = (IAccountService) context.getBean("accountService");
System.out.println(accountService);
IAccountService accountService2 = (IAccountService) context.getBean("accountService");
System.out.println(accountService2);
//accountService.saveAccount();
}
}
输出结果
com.mmj.service.impl.AccountServiceImpl@58134517
com.mmj.service.impl.AccountServiceImpl@58134517
5.1 ApplicationContext三个常用实现类
- ClassPathXmlApplicationContext:加载类路径下的配置文件
- FileSystemXmlApplicationContext:加载磁盘任意位置文件(有权限)
- AnnotationConfigApplicationContext:它是用于读取注解创建容器的
但Spring的容器ApplicationContext和BeanFactory有一些不同。
- ApplicationContext创建容器使用的策略是立即加载的方式,也就是一读取配置文件,就马上创建配置中的文件。
- BeanFactory创建容器的时候,使用的是延迟加载的方式。也就是什么时候根据id创建对象了,才是真正创建对象的时候。
public static void main(String[] args) {
//// IAccountService accountService=new AccountServiceImpl();
// //1. 获取核心容器对象
// ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");
// IAccountService accountService = (IAccountService) context.getBean("accountService");
// System.out.println(accountService);
// IAccountService accountService2 = (IAccountService) context.getBean("accountService");
// System.out.println(accountService2);
// //accountService.saveAccount();
Resource resource = new ClassPathResource("beans.xml");
BeanFactory beanFactory = new XmlBeanFactory(resource);
IAccountService accountService = (IAccountService) beanFactory.getBean("accountService");
System.out.println(accountService);
}
}
这两者的区别在于:
- ApplicationContext在new的时候就已经初始化对象了,也就是在读取配置文件后就开始创建了。
- BeanFactory加载完配置文件还没有创建对象,而是在调用getBean,使用到对象的时候才开始创建。
因此:ApplicationContext适用于单例模式(更多),BeanFactory适用于多例模式。
5.2 Spring中对Bean的管理细节
1. 创建bean的三种方式
<!--第一种方式,使用组件默认构造函数创建,如果没有默认构造函数就会报错-->
<bean id="accountDao" class="com.mmj.dao.impl.AccountDaoImpl"></bean>
<!--第二种方式,使用普通工厂方法创建对象(使用某个类中的方法创建对象,并且存入容器)-->
<bean id="beanFactory" class="com.mmj.factory.InstanceFactory"></bean>
<bean id="accountDao" factory-bean="beanFactory" factory-method="getDao"></bean>
<!--第三种方式,使用工厂中的静态方法创建-->
<bean id="accountDao" class="com.mmj.factory.StaticFactory" factory-method="getStaticDao"></bean>
2. bean对象的作用范围
3. bean对象的生命周期
Spring 框架的概述以及Spring中基于XML的IOC配置的更多相关文章
- 01Spring基于xml的IOC配置--入门
01Spring基于xml的IOC配置 1.创建一个普通的maven工程 1.1 选择maven,不用骨架,点击下一步. 1.2 填写GroupId.ArtifactId.Version.填完点击下一 ...
- spring框架对于实体类复杂属性注入xml文件的配置
spring框架是javaWeb项目中至关重要的一个框架,大多web 项目在工作层次上分为持久层.服务层.控制层.持久层(dao.mapper)用于连接数据库,完成项目与数据库中数据的传递:服务层(s ...
- 03-Spring基于xml的IOC配置--spring的依赖注入
1.概念 依赖注入:Dependency Injection(简称DI注入).它是 spring 框架核心 ioc 的具体实现. 简单理解:可以在一个类中不通过new的方式依赖其它对象.目的是为了解耦 ...
- 02Spring基于xml的IOC配置--实例化Bean的三种方式
maven依赖 <dependencies> <!--IOC相关依赖--> <dependency> <groupId>org.springframew ...
- Spring框架教程IDEA版-----更新中
补充:设计模式中的工厂模式 设计模式党的主要原则:(1)对接口编程,而不是对实现编程 (2)优先使用对象组合而不是继承 在实现接口的方法时: @Override是伪代码,表示重写.(当然不写@Over ...
- Spring中AOP的基于xml开发和配置
pom文件: <?xml version="1.0" encoding="UTF-8"?> <project xmlns="http ...
- Spring中基于xml的AOP
1.Aop 全程是Aspect Oriented Programming 即面向切面编程,通过预编译方式和运行期动态代理实现程序功能的同一维护的一种技术.Aop是oop的延续,是软件开发中的 一个热点 ...
- 基于XML的AOP配置
创建spring的配置文件并导入约束 此处要导入aop的约束 <?xml version="1.0" encoding="UTF-8"?> < ...
- spring框架的概述与入门
1. Spring框架的概述 * Spring是一个开源框架 * Spring是于2003 年兴起的一个轻量级的Java开发框架,由Rod Johnson在其著作Expert One-On-One J ...
随机推荐
- 实训作业5(lang、util)
实验内容和原理: 1.将布尔型.整型.长整型.双精度型作为参数,实例化相应的包装类对象,并输出对象的数值. package 包装; public class integer { public stat ...
- Xamarin Forms 实现发送通知点击跳转
1. Ensure the you have set LaunchMode.SingleTop on your MainActivity: LaunchMode.SingleTop [Activity ...
- 洛谷 P1351 联合权值 题解
P1351 联合权值 题目描述 无向连通图 \(G\) 有 \(n\) 个点,\(n-1\) 条边.点从 \(1\) 到 \(n\) 依次编号,编号为 \(i\) 的点的权值为 \(W_i\),每条 ...
- Day17:web前端开发面试题
1.JavaScript 数据类型有哪些? JavaScript 变量能够保存多种数据类型:数值.字符串值.数组.对象等等: var length = 7; // 数字 var lastName = ...
- mysql 组合聚集函数
mysql> select * from table1; +----------+------------+-----+---------------------+ | name_new | t ...
- Truncate使用注意事项
1.TRUNCATE TABLE 在功能上与不带 WHERE 子句的 DELETE 语句相同:二者均删除表中的全部行.但 TRUNCATE TABLE 比 DELETE 速度快,且使用的系统和事务日志 ...
- Apache ranger整合hive报错记录
版本信息如下: hadoop2.9.2 hive 2.x ranger 最新版2.1.0 在hive端部署完ranger 插件以后,在使用beeline连接查询数据库时报错,报错信息如下: verbo ...
- avalon $computed不起作用?
computed写的个数,应该是只能一个的,之前写了两个,一个是空,一个里面有数据,那个有数据的不起作用,但是在有数据的里面写一个一个console.log就会起作用,所以将多余的空的computed ...
- 定制比特币btc地址address
https://99bitcoins.com/how-to-get-a-custom-bitcoin-address/ https://en.bitcoin.it/wiki/Vanitygen htt ...
- 软件定义网络基础---REST API的设计规范
一:REST API的设计 REST API是基于HTTP协议进行设计的,由HTTP动词+URI组成 (一)HTTP动词 (二)资源的原型 文档(Document): 文档是资源的单一表现形式: 集合 ...