Spring框架是由于软件开发的复杂性而创建的,它是分层的 Java SE/EE应用 full-stack 轻量级开源框架。
它以 IoC(Inverse Of Control: 反转控制)和 AOP(Aspect Oriented Programming:面向切面编程)为内核,提供了展现层 Spring MVC 和持久层 Spring JDBC 以及业务层事务管理等众多的企业级应用技术,还能整合开源世界众多 著名的第三方框架和类库,逐渐成为使用最多的Java EE 企业应用开源框架。
方便解耦,简化开发
通过 Spring提供的 IoC容器,可以将对象间的依赖关系交由 Spring进行控制,避免硬编码所造成的过度程序耦合。用户也不必再为单例模式类、属性文件解析等这些很底层的需求编写代码,可以更专注于上层的应用。
AOP编程的支持
通过 Spring的 AOP 功能,方便进行面向切面的编程,许多不容易用传统OOP 实现的功能可以通过 AOP 轻松应付。
声明式事务的支持
可以将我们从单调烦闷的事务管理代码中解脱出来,通过声明式方式灵活的进行事务的管理, 提高开发效率和质量。
方便程序的测试
可以用非容器依赖的编程方式进行几乎所有的测试工作,测试不再是昂贵的操作,而是随手可做的事情。
方便集成各种优秀框架
Spring可以降低各种框架的使用难度,提供了对各种优秀框架(Struts、Hibernate、Hessian、Quartz 等)的直接支持。
降低 JavaEE API的使用难度
Spring对 JavaEE API(如 JDBC、JavaMail、远程调用等)进行了薄薄的封装层,使这些 API 的使用难度大为降低。
今天我们只讲解Spring的IoC(反转控制)。
Spring通过一种称作控制反转(IoC)的技术促进了松耦合。当应用了IoC,一个对象依赖的其它对象会通过被动的方式传递进来,而不是这个对象自己创建或者查找依赖对象。你可以认为IoC与JNDI相反——不是对象从容器中查找依赖,而是容器在对象初始化时不等对象请求就主动将依赖传递给它。
下面我们通过spring IoC来实现之前工厂模式的案例
持久层接口IStudentDao
package dao;
/**
* 持久层接口
*/
public interface IStudentDao {
/**
* 模拟查询所有
*/
void findAll();
}
持久层实现类StudentDaoImpl
package dao.impl;
import dao.IStudentDao;
/**
* 持久层实现类
*/
public class StudentDaoImpl implements IStudentDao {
@Override
public void findAll(){
System.out.println("查找到所有学生记录。");
}
}
业务逻辑层接口IStudentService
package service;
/**
* 业务层的接口
*/
public interface IStudentService {
/**
* 模拟查询
*/
void findAll();
}
业务逻辑层实现类StudentServiceImpl
package service.impl;
import dao.IStudentDao;
import dao.impl.StudentDaoImpl;
import service.IStudentService;
/**
* 业务层实现类
*/
public class StudentServiceImpl implements IStudentService {
private IStudentDao studentDao;
@Override
public void findAll(){
studentDao.findAll();
}
}
在类的根路径下创建一个任意名称的 xml 文件,让 spring 管理资源,在配置文件中配置 service 和 dao
bean.xml
<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">
<bean id="studentServiceImpl" class="service.impl.StudentServiceImpl">
<property name="studentDao" ref="studentDao">property>
bean>
<bean id="studentDao" class="dao.impl.StudentDaoImpl">bean>
beans>
bean标签作用:
用于配置对象让 spring 来创建的,默认情况下它调用的是类中的无参构造函数。如果没有无参构造函数则不能创建成功。
属性:
id:给对象在容器中提供一个唯一标识。用于获取对象。
class:指定类的全限定类名。用于反射创建对象。默认情况下调用无参构造函数。
scope:指定对象的作用范围。
* singleton :默认值,单例的.
* prototype :多例的.
* request :WEB 项目中,Spring 创建一个 Bean 的对象,将对象存入到 request 域中.
* session :WEB 项目中,Spring 创建一个 Bean 的对象,将对象存入到 session 域中.
* global session :WEB 项目中,应用在 Portlet 环境.如果没有 Portlet 环境那么 globalSession 相当于 session.
init-method:指定类中的初始化方法名称。
destroy-method:指定类中销毁方法名称。
单例对象:scope="singleton"
一个应用只有一个对象的实例。它的作用范围就是整个引用。
生命周期:
对象创建:当应用加载,创建容器时,对象就被创建了。
对象存活:只要容器在,对象一直活着。
对象销毁:当应用卸载,销毁容器时,对象就被销毁了。
多例对象:scope="prototype"
每次访问对象时,都会重新创建对象实例。
生命周期:
对象创建:当使用对象时,创建新的对象实例。
对象存活:只要对象在使用中,就一直活着。
对象销毁:当对象长时间不用时,被 java 的垃圾回收器回收了。
spring中的依赖注入
依赖注入:
Dependency Injection
IOC的作用:
降低程序间的耦合(依赖关系)
依赖关系的管理:
以后都交给spring来维护
在当前类需要用到其他类的对象,由spring为我们提供,我们只需要在配置文件中说明
依赖注入:
能注入的数据:有三类
基本类型和String
其他bean类型(在配置文件中或者注解配置过的bean)
复杂类型/集合类型
注入的方式:有三种
第一种:使用构造函数提供
第二种:使用set方法提供
第三种:使用注解提供
构造函数注入
使用的标签:constructor-arg
标签出现的位置:bean标签的内部
标签中的属性
type:用于指定要注入的数据的数据类型,该数据类型也是构造函数中某个或某些参数的类型
index:用于指定要注入的数据给构造函数中指定索引位置的参数赋值。索引的位置是从0开始
name:用于指定给构造函数中指定名称的参数赋值 常用的
value:用于提供基本类型和String类型的数据
ref:用于指定其他的bean类型数据。它指的就是在spring的Ioc核心容器中出现过的bean对象
优势:
在获取bean对象时,注入数据是必须的操作,否则对象无法创建成功。
弊端:
改变了bean对象的实例化方式,使我们在创建对象时,如果用不到这些数据,也必须提供。
示例:
<bean id="testbean" class="Testbean">
<constructor-arg name="name" value="jack">constructor-arg>
<constructor-arg name="age" value="18">constructor-arg>
bean>
set方法注入
标签:property
出现的位置:bean标签的内部
标签的属性
name:用于指定注入时所调用的set方法名称
value:用于提供基本类型和String类型的数据
ref:用于指定其他的bean类型数据。它指的就是在spring的Ioc核心容器中出现过的bean对象
优势:
创建对象时没有明确的限制,可以直接使用默认构造函数
弊端:
如果有某个成员必须有值,则获取对象是有可能set方法没有执行。
示例:
<bean id="testbean" class="Testbean">
<property name="name" value="jack" >property>
<property name="age" value="18">property>
bean>
复杂类型的注入/集合类型的注入
用于给List结构集合注入的标签:
list array set
用于个Map结构集合注入的标签:
map props
嵌套在property中使用
示例:
<bean id="testbean" class="Testbean">
<property name="mySet">
<set>
<value>Avalue>
<value>Bvalue>
set>
property>
<property name="myArray">
<array>
<value>Avalue>
<value>Bvalue>
array>
property>
<property name="myList">
<list>
<value>Avalue>
<value>Bvalue>
list>
property>
<property name="myMap">
<props>
<prop key="key1">1prop>
<prop key="key2">2prop>
props>
property>
<property name="myProps">
<map>
<entry key="key1" value="1">entry>
map>
property>
bean>
测试代码
package ui;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import service.IStudentService;
import service.impl.StudentServiceImpl;
public class Client {
public static void main(String[] args) {
ApplicationContext ac = new ClassPathXmlApplicationContext("bean.xml");
IStudentService as = (StudentServiceImpl)ac.getBean("studentServiceImpl");
IStudentService as1 = (StudentServiceImpl)ac.getBean("studentServiceImpl");
as.findAll();
// 判断对象是否单例
System.out.println(as==as1);
}
}
运行结果如下:
查找到所有学生记录。
true
今天的分享就到这里了,希望大家能够有所收获,欢迎关注。