Spring(一)、下载,概述.监听器
2018-11-26 07:56:11来源:博客园 阅读 ()
Spring4 学习路线
Spring 第一天:Spring的概述、SpringIOC入门(XML)、Spring的Bean管理、Spring属性注入
Spring 第二天:Spring的IOC的注解方式、Spring的AOP开发(XML)
Spring 第三天:Spring的AOP的注解开发、Spring的声明式事务、JdbcTemplate。
Spring 第四天:SSH的整合、HibernateTemplate的使用、OpenSessionInViewFilter的使用。
1、Spring的概述
1.1、Spring的概述
1.1.1、什么是Spring
轻量:创建一个对象的时候不会耗费太长的时间,创建每一个对象的开销都是非常小的。
Spring:SE/EE开发的一站式框架。
一站式框架:有EE开发的每一层解决方案。
WEB层 :SpringMVC
Service层 :Spring的Bean管理,Spring声明式事务
DAO层 :Spring的Jdbc模板,Spring的ORM模块
1.1.2、为什么学习Spring
1.1.3、Spring的版本
目前流行的版本 Spring3.x 和 Spring4.x
Spring3.x:主要用于整合 Hibernate3.x 版本的;Spring4.x:去整合 Hibernate5.x 的版本。
2、Spring的入门(IOC)
2.1、什么IOC
IOC: Inversion of Control(控制反转)。
控制反转:将对象的创建权反转给(交给)Spring。
2.2、下载Spring的开发包
官网:http://spring.io/
2.3、解压Spring的开发包
docs :Spring的开发规范和API
libs :Spring的开发的jar和源码
schema :Spring的配置文件的约束
2.4、创建web项目,引入jar包
当前做的是 IOC 的入门,所有只引这四个包。
其实 Spring 在进行基本开发的时候,是需要有日志记录的,所以还需要引入日志记录的。Spring 里面没有,需要去依赖库里边找
Apache 提供的日志接口规范,里面定义的都是接口规范,具体做实现的还是 log4j。
2.5、创建接口和类
UserDAO.java
package com.itheima.spring.demo1; /** * 用户管理DAO层接口 * @author jt * */ public interface UserDAO { public void save(); }
UserDAOImpl.java
package com.itheima.spring.demo1; /** * 用户管理DAO层实现类 * @author jt * */ public class UserDAOImpl implements UserDAO { private String name; public void setName(String name) { this.name = name; } @Override public void save() { System.out.println("UserDAOImpl执行了..."+name); } }
问题:
如果底层的实现切换了,需要修改源代码,能不能不修改程序源代码对程序进行扩展?
介绍的这一段,就是 Spring IOC 的底层实现。其实 IOC 的底层实现,就是通过工工厂+反射+配置文件,来实现程序的解耦和的。Spring 框架的出现,就是为了解决我们实际开发中出现的一些问题,比如 MySQL 数据库不行了,需要改成 Oracle 数据库的一套实现,有可能需要去改程序的源代码,一改就需要改很多。因为不可能就一个模块,一个项目中几十个、几百个都有可能。改一个 DAO 的实现类,好多 Service 都需要改,一改就需要改好多;那么现在就不需要了,只需要在配置文件中一修改,程序的源代码不用变。
2.6、将实现类交给Spring管理
在spring的解压路径下spring-framework-4.2.4.RELEASE\docs\spring-framework-reference\html\xsd-configuration.html
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:p="http://www.springframework.org/schema/p" 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"> <!-- Spring的入门的配置==================== --> <bean name="userDAO" class="com.itheima.spring.demo1.UserDAOImpl" > </bean>
2.7、编写测试类
@Test /** * 传统方式的调用 */ public void demo1(){ UserDAOImpl userDAO = new UserDAOImpl(); userDAO.setName("王东"); userDAO.save(); } @Test /** * Spring的方式的调用 */ public void demo2(){ // 创建Spring的工厂 ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); UserDAO userDAO = (UserDAO) applicationContext.getBean("userDAO"); userDAO.save(); }
切换底层的实现类,不需要改写任何的代码,只需要加上 UserDAOHibernateImpl。只需要一改配置文件,不用要改变程序任何的代码。
<bean name="userDAO" class="com.itheima.spring.demo1.UserDAOHibernateImpl" >
其实 Spring 在使用的时候还是挺简单的,就是把你自己写的一个类,配置到 Spring 的配置文件里边去;然后再调用这个类的提携方法的时候,通过工厂的方式来获得这个类的实例就可以了。
2.8、IOC和DI(*****)
IOC:控制反转,将对象的创建权反转给了Spring。
DI:依赖注入,前提必须有IOC的环境,Spring管理这个类的时候将类的依赖的属性注入(设置)进来。
面向对象的时候,类和类之间是有一些关系的
1、依赖
Class A{ } Class B{ public void xxx(A a){ } }
B 类依赖 A 类,在 Spring 中可以把 A 的值设置进来,前提是这个类必须交给 Spring 管。Spring 在创建这个类的时候,会把这个类依赖的属性设置进来。
2、继承:is a
Class A{ } Class B extends A{ }
3、聚合:has a
聚合有两类,一类是松散的,一类是紧密的。
例:假设在 DAO 的实现类当中,需要依赖一个属性,比如说就是 name;需要提供 set 方法,设置值 set 就可以了。这就说明了,这个类依赖了一个字符串属性。
package com.itheima.spring.demo1; /** * 用户管理DAO层实现类 * @author jt * */ public class UserDAOImpl implements UserDAO { private String name; public void setName(String name) { this.name = name; } @Override public void save() { System.out.println("UserDAOImpl执行了..."+name); } }
那么,传统方式想给属性设置一个值。注意,不能用接口设置了,接口没有这个属性,必须把它变成具体的实现类。
想给某一个类里面的属性设置值,比较麻烦。第一不能面向接口编程了;第二,还需要手动调用这个方法,也得去该变程序的圆脑袋妈妈。
@Test /** * 传统方式的调用 */ public void demo1(){ UserDAOImpl userDAO = new UserDAOImpl(); userDAO.setName("王东"); userDAO.save(); }
Spring 可以把这个类依赖的属性自动设置进来,前提是这个类需要交给 Spring 管。Spring 在管理这个类,需要通过一个标签,写上属性名和值。
<!-- Spring的入门的配置==================== -->
<bean name="userDAO" class="com.itheima.spring.demo1.UserDAOImpl" >
<property name="name" value="李东"/>
</bean>
@Test /** * Spring的方式的调用 */ public void demo2(){ // 创建Spring的工厂 ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); UserDAO userDAO = (UserDAO) applicationContext.getBean("userDAO"); userDAO.save(); }
这就可以了,运行 demo2,值可以取出来(设置进去了)。设置值的过程就叫做 DI,就是 Spring 在帮我们创建这个类的实例的过程当中,发现这个了里边有一个属星(这叫依赖)。那么它就帮我们把这个属性设置进来,通过配置就把属性设置进来,这种就叫做 DI。
IOC 指的是把这类交给 Spring 管理了,DI 指的是 Spring 在管理这个类的过程当中把这个类的属性给你设置进来。
3、Spring的工厂类
3.1、Spring的工厂类
3.1.1、Spring工厂类的结构图
ApplicationContext继承BeanFactory。
3.1.2、BeanFactory :老版本的工厂类
BeanFactory:调用getBean的时候,才会生成类的实例。
3.1.3、ApplicationContext :新版本的工厂类
ApplicationContext:加载配置文件的时候,就会将Spring管理的类(其实是单例模式创建的类)都实例化。比如配置文件配置三个类,加载配置文件的时候都会 new 出来。
ApplicationContext有两个实现类
ClassPathXmlApplicationContext :加载类路径下(其实指的就是 SRC里边的东西最终会被翻译到 web-inf 下 class下)的配置文件
FileSystemXmlApplicationContext :加载文件系统下(某个硬盘下的)的配置文件
@Test /** * 加载磁盘上的配置文件 */ public void demo3(){ ApplicationContext applicationContext = new FileSystemXmlApplicationContext("C:\\applicationContext.xml"); UserDAO userDAO = (UserDAO) applicationContext.getBean("userDAO"); userDAO.save(); }
子类有比父类更强大的功能,所以现在一般用的都是子类对象。
4、Spring的配置
4.1、XML的提示配置
跟原来 DTD 方式不同
4.1.1、Schema的配置
一个 XML 文件是被一个 DTD 文档约束的,但是可以被多个 Schema 约束。
4.2、Bean的相关的配置
4.2.1、<bean>标签的id和name的配置
id :使用了约束中的唯一约束。里面不能出现特殊字符的。
name :没有使用约束中的唯一约束(理论上可以出现重复的,但是实际开发不能出现的)。里面可以出现特殊字符。重复 name ,在 getBean 的时候生成实例时会报错,不知道生成那个对象的实例。
Spring和Struts1框架整合的时候,name 属性值前面必须 要加上 “”/,需要注意,<bean name=”/user” class=””/>。其他版本无所谓的
class :要生成实例的类的全路径,根据属性值帮你生成类的实例。
4.2.2、Bean的生命周期的配置(了解)
init-method :Bean被初始化的时候执行的方法
Spring 帮你创建这个类,在帮你创建这个类的时候,给你提供了一个初始化的方法。当这个类一被实例化,这个方法就会自动执行。
destroy-method :Bean被销毁的时候执行的方法(Bean是单例创建,工厂关闭,默认是单例创建的)
<!-- Spring的sBean的生命周期的配置=========== --> <bean id="customerDAO" class="com.itheima.spring.demo2.CustomerDAOImpl" scope="prototype" init-method="setup" destroy-method="destroy"/>
CustomerDAOImpl.java
package com.itheima.spring.demo2; public class CustomerDAOImpl implements CustomerDAO { public void setup(){ System.out.println("CustomerDAOImpl被初始化了..."); } @Override public void save() { System.out.println("CustomerDAOImpl的save方法执行了..."); } public void destroy(){ System.out.println("CustomerDAOImpl被销毁了..."); } }
SpringDemo2.java
@Test /** * 生命周期的配置 */ public void demo1(){ ClassPathXmlApplicationContext applicationContext= new ClassPathXmlApplicationContext("applicationContext.xml"); CustomerDAO customerDAO = (CustomerDAO) applicationContext.getBean("customerDAO"); customerDAO.save(); applicationContext.close(); // (如果这个类是被单例创建的,会被销毁) }
4.3、Bean的作用范围的配置(重点)
scope :Bean的作用范围
singleton :默认的,Spring会采用单例模式创建这个对象。
prototype :多例模式。(Struts2 和 Spring 整合一定会用到)
整合的时候会用到,Action 类 也可以交给 Spring 去管理。但是,Action 类在 Struts2 那边多例的,所以说一旦把 Action 类交给 Spring 去管理了,就要把这个值配置上。
request :应用在web项目中,Spring 创建这个类以后,将这个类存入到request范围中。
session :应用在web项目中,Spring 创建这个类以后,将这个类存入到session范围中。
globalsession :应用在web项目中,必须在 porlet 环境下使用。但是如果没有这种环境,相对于 session。
<!-- Spring的sBean的生命周期的配置=========== --> <bean id="customerDAO" class="com.itheima.spring.demo2.CustomerDAOImpl" scope="prototype" init-method="setup" destroy-method="destroy"/>
@Test /** * Bean的作用范围配置 */ public void demo2(){ ClassPathXmlApplicationContext applicationContext= new ClassPathXmlApplicationContext("applicationContext.xml"); CustomerDAO customerDAO1 = (CustomerDAO) applicationContext.getBean("customerDAO"); System.out.println(customerDAO1); CustomerDAO customerDAO2 = (CustomerDAO) applicationContext.getBean("customerDAO"); System.out.println(customerDAO2); System.out.println(customerDAO1==customerDAO2); applicationContext.close(); }
5、Spring的Bean管理(XML方式)
5.1、Spring的Bean的实例化方式(了解)
Bean 已经都交给 Spring 管理,Spring 创建这些类的时候,有几种方式:
package com.itheima.spring.demo3; import org.junit.Test; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; /** * Bean的实例化的方式 * @author jt * */ public class SpringDemo3 { @Test /** * 无参数构造方法 */ public void demo1(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Bean1 bean1 = (Bean1) applicationContext.getBean("bean1"); } @Test /** * 静态工厂实例化 */ public void demo2(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Bean2 bean2 = (Bean2) applicationContext.getBean("bean2"); System.out.println(bean2); } @Test /** * 实例工厂实例化 */ public void demo3(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Bean3 bean3 = (Bean3) applicationContext.getBean("bean3"); System.out.println(bean3); } }
5.1.1、无参构造方法的方式(默认)
编写类
package com.itheima.spring.demo3; /** * 无参数构造方法方式 * @author jt * */ public class Bean1 { public Bean1() { super(); System.out.println("Bean1的无参数的构造方法执行了..."); } }
编写配置
<!-- Spring的Bean的实例化的方式============= --> <!-- 无参数构造方法 --> <bean id="bean1" class="com.itheima.spring.demo3.Bean1"></bean>
5.1.2、静态工厂实例化的方式
编写Bean2的静态工厂
package com.itheima.spring.demo3; /** * 静态工厂实例化方式 * @author jt * */ public class Bean2 { }
package com.itheima.spring.demo3; /** * Bean2的静态工厂 * @author jt * */ public class Bean2Factory { public static Bean2 createBean2(){ System.out.println("Bean2Factory中方法执行了..."); return new Bean2(); } }
配置
<!-- 静态工厂实例化 --> <bean id="bean2" class="com.itheima.spring.demo3.Bean2Factory" factory-method="createBean2"/>
5.1.3、实例工厂实例化的方式
Bean3的实例工厂
package com.itheima.spring.demo3; /** * 实例工厂实例化的方式 * @author jt * */ public class Bean3 { }
package com.itheima.spring.demo3; /** * Bean3的实例工厂 * @author jt * */ public class Bean3Factory { public Bean3 createBean3(){ System.out.println("Bean3的实例工厂执行了..."); return new Bean3(); } }
配置
<!-- 实例工厂实例化 --> <bean id="bean3Factory" class="com.itheima.spring.demo3.Bean3Factory"></bean> <bean id="bean3" factory-bean="bean3Factory" factory-method="createBean3"></bean>
5.2、Spring的属性注入
5.2.1、构造方法的方式的属性注入
构造方法的属性注入
<!-- 构造方法的方式 --> <bean id="car" class="com.itheima.spring.demo4.Car"> <constructor-arg name="name" value="宝马"/> <constructor-arg name="price" value="800000"/> </bean>
5.2.2、Set方法的方式的属性注入
Set 方法的属性注入
<!-- set方法的方式 --> <bean id="car2" class="com.itheima.spring.demo4.Car2"> <property name="name" value="奔驰"/> <property name="price" value="1000000"/> </bean>
Set 方法设置对象类型的属性
<!-- set方法注入对象类型的属性 --> <bean id="employee" class="com.itheima.spring.demo4.Employee"> <!-- value:设置普通类型的值,ref:设置其他的类的id或name --> <property name="name" value="涛哥"/> <property name="car2" ref="car2"/> </bean>
底部
package com.itheima.spring.demo4; import org.junit.Test; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; /** * 属性注入的方式: * @author jt * */ public class SpringDemo4 { @Test /** * 构造方法方式的属性注入 */ public void demo1(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Car car = (Car) applicationContext.getBean("car"); System.out.println(car); } @Test /** * set方法方式的属性注入 */ public void demo2(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Car2 car2 = (Car2) applicationContext.getBean("car2"); System.out.println(car2); } @Test /** * set方法注入对象类型 */ public void demo3(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Employee employee = (Employee) applicationContext.getBean("employee"); System.out.println(employee); } }
5.2.3、P 名称空间的属性注入(Spring2.5以后)
通过引入p名称空间完成属性的注入:
写法:
普通属性 p:属性名=”值”
对象属性 p:属性名-ref=”值”
P名称空间的引入
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:p="http://www.springframework.org/schema/p" 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">
使用p名称空间
<!-- 改为p名称空间的方式 --> <!-- <bean id="car2" class="com.itheima.spring.demo4.Car2" p:name="奇瑞QQ" p:price="30000"></bean> <bean id="employee" class="com.itheima.spring.demo4.Employee" p:name="王东" p:car2-ref="car2"></bean> -->
5.2.4、SpEL的属性注入(Spring3.0以后)
SpEL:Spring Expression Language,Spring的表达式语言。
语法:
#{SpEL}
<!-- SpEL的属性注入 --> <bean id="carInfo" class="com.itheima.spring.demo4.CarInfo"> </bean> <bean id="car2" class="com.itheima.spring.demo4.Car2"> <property name="name" value="#{carInfo.name}"></property> <property name="price" value="#{carInfo.calculatorPrice()}"></property> </bean> <bean id="employee" class="com.itheima.spring.demo4.Employee"> <property name="name" value="#{'赵洪'}"></property> <property name="car2" value="#{car2}"></property> </bean>
5.3、集合类型属性注入(了解)
5.3.1、配置
<!-- Spring的集合属性的注入============================ --> <!-- 注入数组类型 --> <bean id="collectionBean" class="com.itheima.spring.demo5.CollectionBean"> <!-- 数组类型 --> <property name="arrs"> <list> <value>王东</value> <value>赵洪</value> <value>李冠希</value> </list> </property> <!-- 注入list集合 --> <property name="list"> <list> <value>李兵</value> <value>赵如何</value> <value>邓凤</value> </list> </property> <!-- 注入set集合 --> <property name="set"> <set> <value>aaa</value> <value>bbb</value> <value>ccc</value> </set> </property> <!-- 注入Map集合 --> <property name="map"> <map> <entry key="aaa" value="111"/> <entry key="bbb" value="222"/> <entry key="ccc" value="333"/> </map> </property> </bean>
SpringDemo5.java
package com.itheima.spring.demo5; import org.junit.Test; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; /** * 集合类型的属性注入 * * @author jt * */ public class SpringDemo5 { @Test public void demo1() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); CollectionBean collectionBean = (CollectionBean) applicationContext.getBean("collectionBean"); System.out.println(collectionBean); } }
CollectionBean.java
package com.itheima.spring.demo5; import java.util.Arrays; import java.util.List; import java.util.Map; import java.util.Set; /** * 集合属性的注入: * @author jt * */ public class CollectionBean { private String[] arrs; private List<String> list; private Set<String> set; private Map<String,String> map; public void setArrs(String[] arrs) { this.arrs = arrs; } public void setList(List<String> list) { this.list = list; } public void setSet(Set<String> set) { this.set = set; } public void setMap(Map<String, String> map) { this.map = map; } @Override public String toString() { return "CollectionBean [arrs=" + Arrays.toString(arrs) + ", list=" + list + ", set=" + set + ", map=" + map + "]"; } }
集合类型在自己定义类的时候很少用到,一般是在框架的内部,尤其是 Spring 整合 Hibernate 的时候,有可能把 Hibernate 映射做成一个数组或集合,需要想办法把映射设置进去。
6、Spring的分模块开发的配置
6.1、分模块配置
6.1.1、在加载配置文件的时候,加载多个
public class SpringDemo5 { @Test public void demo1() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml","applicationContext2.xml"); CollectionBean collectionBean = (CollectionBean) applicationContext.getBean("collectionBean"); System.out.println(collectionBean); } }
6.1.2、 在一个配置文件中引入多个配置文件(常用)
applicationContext.xml
<import resource="applicationContext2.xml"/>
Car.java
package com.itheima.spring.demo4; public class Car { private String name; private Double price; public Car(String name, Double price) { super(); this.name = name; this.price = price; } @Override public String toString() { return "Car [name=" + name + ", price=" + price + "]"; } }
Car2.java
package com.itheima.spring.demo4; /** * set方法的属性注入 * @author jt * */ public class Car2 { private String name; private Double price; public void setName(String name) { this.name = name; } public void setPrice(Double price) { this.price = price; } @Override public String toString() { return "Car2 [name=" + name + ", price=" + price + "]"; } }
CarInfo.java
package com.itheima.spring.demo4; public class CarInfo { private String name; public String getName() { return "摩托车"; } public Double calculatorPrice(){ return Math.random() * 3000; } }
Employee.java
package com.itheima.spring.demo4; public class Employee { private String name; private Car2 car2; public void setName(String name) { this.name = name; } public void setCar2(Car2 car2) { this.car2 = car2; } @Override public String toString() { return "Employee [name=" + name + ", car2=" + car2 + "]"; } }
SpringDemo4.java
package com.itheima.spring.demo4; import org.junit.Test; import org.springframework.context.ApplicationContext; import org.springframework.context.support.ClassPathXmlApplicationContext; /** * 属性注入的方式: * @author jt * */ public class SpringDemo4 { @Test /** * 构造方法方式的属性注入 */ public void demo1(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Car car = (Car) applicationContext.getBean("car"); System.out.println(car); } @Test /** * set方法方式的属性注入 */ public void demo2(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Car2 car2 = (Car2) applicationContext.getBean("car2"); System.out.println(car2); } @Test /** * set方法注入对象类型 */ public void demo3(){ ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Employee employee = (Employee) applicationContext.getBean("employee"); System.out.println(employee); } }
标签:
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com
特别注意:本站所有转载文章言论不代表本站观点,本站所提供的摄影照片,插画,设计作品,如需使用,请与原作者联系,版权归原作者所有
- Spring系列.ApplicationContext接口 2020-06-11
- springboot2配置JavaMelody与springMVC配置JavaMelody 2020-06-11
- jdk各个版本下载 2020-06-11
- 给你一份超详细 Spring Boot 知识清单 2020-06-11
- SpringBoot 2.3 整合最新版 ShardingJdbc + Druid + MyBatis 2020-06-11
IDC资讯: 主机资讯 注册资讯 托管资讯 vps资讯 网站建设
网站运营: 建站经验 策划盈利 搜索优化 网站推广 免费资源
网络编程: Asp.Net编程 Asp编程 Php编程 Xml编程 Access Mssql Mysql 其它
服务器技术: Web服务器 Ftp服务器 Mail服务器 Dns服务器 安全防护
软件技巧: 其它软件 Word Excel Powerpoint Ghost Vista QQ空间 QQ FlashGet 迅雷
网页制作: FrontPages Dreamweaver Javascript css photoshop fireworks Flash