一.什么是spring?
1.spring是分层的java SE/EE应用full-stack轻量级开源框架,以IoC(Inverse of controller)反转控制和AOP(Aspect oriented Programming)面向切面编程为内核的,
2.spring的体系结构
3.spring的好处:
*方便解耦,简化开发
*AOP编程的支持
*声明式事务的支持
*方便程序的测试
*方便集成各种优秀框架
*降低javaeeAPI的使用难度
二.spring的核心之IoC(Inverse of Controller):控制反转
1.什么是IoC?
*控制反转是一个重要的面向对象编程的法则来削减计算机程序的耦合问题,也是轻量级spring框架的核心,控制反转一般分为两种类型,一种是依赖注入(Dependency Injection),一种是依赖查找(Dependency Lookup),依赖注入应用比较广泛
2.spring容器简单理解就是用来存放对象的
3.在xml文件中配置bean,就是要把所用到的对象存入到spring容器中
<bean id="userDao" class="com.zjl.spring.dao.impl.UserDaoImpl"></bean>
4.初始化容器和资源的获取
ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
UserDao userDao = (UserDaoImpl)ac.getBean("userDao");
5.springAPI的体系结构
三.spring中的工厂
1.BeanFactory:是在getBean()的时候才会生成类的实例(延迟加载)
*Resource resource = new ClassPathResource("bean.xml");
*BeanFactory factory = new XmlBeanFactory(resource);
2.ApplicationContext:是在加载ApplicationContext.xml的时候就会加载(立即加载),在容器初始化的时候,对象就已经建立好了
3.ApplicationContext的两个实现类:
ClassPathXmlApplicationContext:加载类路径下的spring的配置文件
FileSystemXmlApplicationContext:加载本地磁盘下的spring的配置文件
四.基于xml的IoC配置
1.sprint实例化bean的方式
*调用默认的构造函数:把bean对象交给spring容器来管理,就相当于new出来的一个对象,利用的是反射,但是调用的是默认的构造函数
2.静态工厂实例化:
*<bean id="userBean" class="com.zjl.spring.*" factory-method="getBean">
*class:指的是静态工厂,factory-method指的是获取实例静态方法
3.实例工厂实例化方式
*<bean id="instanceFactory" class="com.zjl.spring.*">
*<bean id="userBean" factory-bean="instanceFactory" factory-method="getBean">
4.bean的作用范围:
*singleton:单例(默认)
*prototype:多例
*request:在web项目中,将对象存入到request请求域中
*session:在web应用中,将对象存入到session会话域中
*globalsession:应用在web项目中,应用porlet环境
*<bean id="" class="" scope="">
5.bean的生命周期:init-method和destory-method
*配置告知spring哪个是初始化方法,哪个是销毁方法
*当bean对象是非单例的时候,spring就不再管理销毁了,也就不会触发销毁方法
五.依赖注入(DI)
1.使用构造函数注入
-
<bean id="user" class="com.zjl.spring.domain.User">
-
<constructor-arg index="1" value="郑金磊"></constructor-arg>
-
<constructor-arg name="job" value="学生"></constructor-arg>
-
<constructor-arg type="java.lang.Integer" value="18"></constructor-arg>
-
<constructor-arg type="java.lang.Integer" value="26"></constructor-arg>
-
<constructor-arg name="birthday" ref="now"></constructor-arg>
-
</bean>
-
<bean id="now" class="java.util.Date"></bean>
*使用constructor-arg元素进行注入:
*index:根据字段在构造函数中出现的索引进行注入,从0开始
*name:根据字段的名称注入
*ref:要注入的值,它可以引用其他bean
*value:要注入的值,注意:它只能是基本类型和String类型
*type:根据字段的类型
2.使用set方法注入
<bean id="now" class="java.util.Date"></bean>
<bean id="user" class="com.zjl.spring.domain.User">
<property name="id" value="1"></property>
<property name="name" value="麦迪"></property>
<property name="job" value="篮球运动员"></property>
<property name="age" value="35"></property>
<property name="birthday" ref="now"></property>
</bean>
*property元素:
*name:要注入的属性名称;
*value:要注入的属性值
*ref:注入引用bean类型的值
3.p名称空间注入
<bean id="user" class="com.zjl.spring.domain.User" p:id="2" p:name="kobe" p:job="player" p:birthday-ref="now"></bean>
4.使用SpEL注入方式
*{SpEL}:
*基本类型或String使用:#{' '}
*引用类型:#{表达式}
<bean id="user" class="com.zjl.spring.domain.User">
<property name="id" value="#{'6'}"></property>
<property name="name" value="#{'阿里'}"></property>
<property name="job" value="拳击"></property>
<property name="age" value="#{33}"></property>
<property name="birthday" value="#{now}"></property>
</bean>
5.数组/集合(list.set.map),properties注入
*数组或者集合
<!-- 注入数组 -->
<property name="myStrs">
<array>
<value>AAA</value>
<value>BBB</value>
<value>CCC</value>
</array>
</property>
<!-- 注入List -->
<property name="myList">
<list>
<value>AAA</value>
<value>BBB</value>
<value>CCC</value>
</list>
</property>
<!-- 注入set-->
<property name="Set">
<set>
<value>AAA</value>
<value>BBB</value>
<value>CCC</value>
</set>
</property>
*map注入有两种方式
<property name="myMap">
<map>
<!-- 第一种方式:使用entry元素和key 及value子元素 -->
<entry>
<key>
<value>test1</value>
</key>
<value>AAA</value>
</entry>
<!-- 第二种方式:直接使用entry元素 -->
<entry key="test2" value="BBB"></entry>
</map>
*properties数组注入:
<!-- 注入properties -->
<property name="myProp">
<props>
<prop key="test1">AAA</prop>
<prop key="test2">BBB</prop>
<prop key="test3">CCC</prop>
</props>
</property>
注意:只要是集合结构相同,元素是可以互换的
6.spring分配置文件开发]
*ApplicationContext ac = new ClassPathXmlApplicationContext("bean1.xml","bean2.xml");
*在同一个配置文件中,不可能有id取值一样的bean
*在不同的配置文件中,可以有id取值相同的bean,后加载的会把先加载的覆盖掉
六.基于注解的IoC配置
1.注解配置的使用前提:
导入spring-ioc必要的jar包
spring-beans-4.2.4.RELEASE.jar
spring-context-4.2.4.RELEASE.jar
spring-core-4.2.4.RELEASE.jar
spring-expression-4.2.4.RELEASE.jar
log4j-1.2.16.jar
commons-logging-1.2.jar
导入spring-aop的一个核心jar包
spring-aop-4.2.4.RELEASE.jar
引入context名称空间
<?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
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd">
</beans>
*在spring配置文件中指定要扫描的包
<context:component-scan base-package="com.zjl">
*在bean上面使用@Component注解
2.spring IoC常见的注解
*@Component
作用:让spring容器管理当前的bean(实例化)
属性:value:指定bean的名称,默认值是当前类的简单名称
*@Component的衍生注解:@Controller @Service @Repository
作用和属性是和@Comonent一样的
特点:
@Controller:一般在表现层
@Service:一般在业务层
@Repository:一般在持久层
*@Autowired
作用:自动按照类型注入需要的对象,当使用了该注解时,setter就不是必须的了
属性:required:是否必须注入成功,默认值是true
注意事项:
当有两个实现接口时,就看变量的名称,如果没有符合的变量名称,就会报错
*@Value
作用:注入基本类型和string
属性:value:SpEL表达式,要注入的值
*@Qualifier
作用:要配合@Autowired一起使用,指定要注入的bean的名称
属性:value:要注入bean的名称
*@Resource
作用:是@Autowired和@Qualifier的结合
属性:name:要注入的bean的名称
*@Scope
作用:指定当前bean的作用范围
属性:value:singleton prototype
七.spring的bean管理的方式比较
1.xml和注解的比较
*xml和注解的各自特点:
*xml:结构清晰
*注解:开发方便
*如果经常修改的配置,用xml文件,如果不经常修改的配置,用注解
*实际开发中还有一种xml和注解整合开发:
*bean由xml配置,但是bean的属性使用注解注入
八.存在的问题:
1.访问servlet:创建spring工厂,不停刷新,不停创建工厂,效率太低
2.解决问题
*第一种方式:将工厂的创建放入到servlet的init方法中,这种方法也是不太好,多个servlet的话,创建一个servlet就创建一个工厂
*第二种方式:将工厂创建好了存入到servletcontext域中,使用工厂的时候,从servletcontext域中获取
*ServletContextListener:用来监听ServletContext对象的创建和销毁
*配置监听器:默认加载WEB-INF下面的名称为application.xml的配置文件
我们也可以指定配置文件的位置,使用配置全局初始化参数
<listener>
<listener-class>
org.springframework.web.context.ContextLoaderListener
</listener-class>
</listener>
<!-- 配置全局初始化参数:指定配置文件的位置-->
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:applicationContext.xml</param-value>
</context-param>
*在Servlet中获取spring容器
WebApplicationContextUtils.getWebAppApplicationContext(ServletContext context)