Spring学习笔记

1. SPring特点

        1--降低了组件之间的耦合性, 实现了软件各个层之间的解耦

                2--可以使用spring容器提供的服务, 如: 事务管理, 消息服务

        3--容器提供单例模式支持

        4--容器提供AOP技术, 利用它很容易实现权限拦截, 运行期监控

        5--容器提供了众多的辅助类, 能加快应用的开发(org.springframework.jdbc.core.JDBCTemplate 等)

        6--spring对主流的应用框架提供了集成支持, 例如: hibernate,JPA, Struts, Mybatis(IBatis)

        7--Spring属于低侵入式设计, 代码污染度极低

        8--独立于各种应用服务器

        9--spring的DI机制降低了业务对象替换的复杂性

        10--spring的高度开发性, 并不强制应用完全依赖于spring, 开发者可以自由选择spring的部分或者全部

2. Spring核心容器模块的组成

 

1、Spring core:核心容器
核心容器提供spring框架的基本功能。Spring以bean的方式组织和管理Java应用中的各个组件及其关系。Spring使用BeanFactory来产生和管理Bean,它是工厂模式的实现。BeanFactory使用控制反转(IoC)模式将应用的配置和依赖性规范与实际的应用程序代码分开。BeanFactory使用依赖注入的方式提供给组件依赖。主要实现控制反转IoC和依赖注入DI、Bean配置以及加载。

2、Spring AOP:Spring面向切面编程
通过配置管理特性,Spring AOP 模块直接将面向方面的编程功能集成到了Spring框架中。

AOP的实现原理为动态代理技术,一共有两种代理模式:

(1)ProxyFactoryBean代理工厂对象

(2)TransactionProxyFactoryBean事务代理工厂对象

3、Spring context:Spring上下文
Spring上下文是一个配置文件,向Spring框架提供上下文信息。

4、Spring DAO
DAO模块主要目的是将持久层相关问题与一般的的业务规则和工作流隔离开来。

5、Spring ORM(Object Relation Mapper)对象关系映射模块
Spring 与所有的主要的ORM框架都集成的很好,包括hibernate、JDO实现、TopLink和IBatis SQL Map等。

6、Spring Web模块
Web模块建立在应用程序上下文模块之上,为基于Web的应用程序提供了上下文。

7、Spring MVC
MVC框架是一个全功能的构建Web应用程序的MVC实现。通过策略接口,MVC框架变成为高度可配置的。

3. SpringWeb模块的组成

Web模块建立在应用程序上下文模块之上,为基于Web的应用程序提供了上下文。

4. ApplicationContext 以及实现类

ApplicationContext,也称为控制反转(IoC)容器,是Spring框架的核心

ApplicationContext的三个实现类说明
 

ApplicationContext的三个实现类说明
ClassPathXmlApplicationContext(常用)加载类路径下的配置文件,要求配置文件必须在类路径下
FileSystemXmlApplicationContext可以加载磁盘任意路径下的配置文件(必须要有访问权限)
AnnotationContigApplicationContext用于读取注解创建容器

在这里插入图片描述

 spring容器原理浅析:

        ①利用dom4j技术,解析XML配置文件,获取里面所有的信息。
        ②根据class属性的值,利用反射创建对象。
        ③将利用反射创建出的对象放入到map中,key就是它所对应的id值。

        BeanFactory和ApplicationContext 的区别     

                (1)ApplicationContext
                        ApplicationContext在构建核心容器时,创建对象采取的是立即加载的方式。也就是说,只要一读取完配置文件马上就创建配置文件中配置的对象。

                (2)BeanFactory
                        BeanFactory在构建核心容器时,创建对象采取的策略是采用延迟加载的方式。也就是说,什么时候根据id获取对象了,什么时候才真正的创建对象。

5. 什么是Spring的依赖注入DI?

        依赖注入是一种消除类之间依赖关系的设计模式。例如,A类要依赖B类,A类不再直接创建B类,而是把这种依赖关系配置在外部xml文件(或java config文件)中,然后由Spring容器根据配置信息创建、管理bean类。

6. 什么是Spring的控制反转IOC

        IOC(Inversion of Control)控制反转:是一种设计思想,是一个重要的面向对象编程的法则,使用这种思想可以让我们设计出低耦合、更加优良的程序。

        IOC是Spring中的核心,它主要的特点就是:调用类中的方法不是通过new它的对象来实现,而是通过Spring配置来创建对象,然后交给IOC容器来管理我们的对象,使用时去找IOC容器要,根本就不用去管我们需要的这个对象时怎么创建的、什么时候被销毁。

        这样一来,类和类之间的关系就变弱了,因为我们没有在一个类中new另一个对象,对象之间的调用、联系都是通过这个IOC容器来获取的,使每一个对象都相对比较独立

即:

  • 原本我们自己手动控制对象(创建和销毁,对象的生命周期
  • 变成了现在交给IOC容器控制对象(创建和销毁)、我们使用时只需要去容器中获取即可

Spring IOC底层运用的技术包括xml配置文件、dom4j解析xml、工厂设计模式、反射,这四种技术

7. 依赖注入的实现方式:Setter注入,构造注入

1.setter方法注入

setter方法注入即是创建一个普通的JavaBean类,为需要注入的属性通过对应的setter方法即可,如:

(1)创建一个Id类:

   

 public class Id {  
        private int id;  
        private String name;  
        public int getId() {  
            return id;  
        }  
        public void setId(int id) {  
            this.id = id;  
        }  
        public String getName() {  
            return name;  
        }  
        public void setName(String name) {  
            this.name = name;  
        }  
    }  

(2)创建配置文件Id_Bean.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  
               http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">  

        <bean id="id" class="com.loster.li.Id">  
        <property name="id" value="123"></property>  
        <property name="name" value="xiaoli"></property>  
        </bean>  
    </beans>  

2.构造方法注入

(1)创建一个Id类:

public class Id {  
        private int id;  
        private String name;  
        public Id(int id,String name){  
            this.id = id;  
            this.name = name;  
        }  
        public int getId() {  
            return id;  
        }  
        public void setId(int id) {  
            this.id = id;  
        }  
        public String getName() {  
            return name;  
        }  
        public void setName(String name) {  
            this.name = name;  
        }  
    }  
<?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  
               http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">  

        <bean id="id" class="com.loster.li.Id">  
        <constructor-arg index="0" value="456"></constructor-arg>  
        <constructor-arg index="1" value="dawang"></constructor-arg>  
        </bean>  
    </beans> 

8. Spring如何实例化Bean。三种方法(构造方法、静态工厂方法实例化、实例工厂方法实例化)

  • 用构造器来实例化
    • 无参构造器(默认构造器)
      • 定义一个实体类,提供空的构造方法,并且提供get和set方法,重写toString方法方便看输出
        • public class Users {
              private String id;
              private String name;
              /**
               * 空的构造方法
               */
              public Users() {
                  super();
                  // TODO Auto-generated constructor stub
              }
              //======使用空的构造方法必须给属性添加get和set方法============
              public String getId() {
                  return id;
              }
              public void setId(String id) {
                  this.id = id;
              }
              public String getName() {
                  return name;
              }
              public void setName(String name) {
                  this.name = name;
              }
              @Override
              public String toString() {
                  return "Users [id=" + id + ", name=" + name + "]";
              }
          }

        • 配置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
           http://www.springframework.org/schema/beans/spring-beans.xsd">
           
           //这就是通过无参构造器实例化bean的方法
          <bean id="user" class="spring_di.Users">
              <property name="id" value="12345678"></property>  //name对应的是属性名字 value对应的是值
              <property name="name" value="小莫"></property>
          </bean>
          </beans>

    • 有参构造器
  • 使用 静态工厂方法实例化
    • 编写实体类
      • public class Users {
            private String id;
            private String username;
        
            @Override
            public String toString() {
                return "Users [id=" + id + ", username=" + username + "]";
            }
        
            public String getId() {
                return id;
            }
        
            public void setId(String id) {
                this.id = id;
            }
        
            public String getUsername() {
                return username;
            }
        
            public void setUsername(String username) {
                this.username = username;
            }
        }
    • 编写工厂类,注意这个工厂的getUserStance()为静态的

      • public class Factory {
            
            public static Users getUserStance()   //getUserStance()为静态的
            {
                System.out.println("getUserStance()");
                return new Users();
            }
        
        }
        
        配置beans.xml文件
        
        ```java
        <bean id="users" class="test.Factory" factory-method="getUserStance"></bean>
        factory-method="getUserStance" 是工厂类里面获取目标实例的方法

  • 使用非静态工厂方法实例化
    • 修改一下工厂类,将getUserStance()改为非静态的方法
      • public class Factory { public Users getUserStance() //非静态的 { System.out.println("getUserStance()"); return new Users(); } }
      • <bean id="factory" class="test.Factory"></bean> <bean id="users" factory-bean="factory" factory-method="getUserStance"></bean>

9. Spring的Bean常见的范围(单例模式、原型模式)

单例模式:(The Singleton Scope):Spring默认机制始终用的是一个bean的实例,共享一个对象     

原型模式(The Prototype Scope):每次从容器中get的时候,都会产生一个新对象!   

10. 了解Spring Bean的生命周期

        对于普通的 Java 对象,当 new 的时候创建对象,然后该对象就能够使用了。一旦该对象不再被使用,则由 Java 自动进行垃圾回收。而 Spring 中的对象是 bean,bean 和普通的 Java 对象没啥大的区别,只不过 Spring 不再自己去 new 对象了,而是由 IoC 容器去帮助我们实例化对象并且管理它,我们需要哪个对象,去问 IoC 容器要即可。IoC 其实就是解决对象之间的耦合问题,Spring Bean 的生命周期完全由容器控制。

        的 Spring Bean 的生命周期主要指的是 singleton bean,对于 prototype 的 bean ,Spring 在创建好交给使用者之后则不会再管理后续的生命周期。

        在Spring中使用Scope来表示一个bean定义对应产生实例的类型,也可以说是对应实例的作用范围。Spring内置支持的scope严格来说默认是有五种,分别是:

singleton:这是默认Scope,表示在整个bean容器中或者说是整个应用中只会有一个实例。
prototype:多例类型,表示每次从bean容器中都会获取到一个对应bean定义全新的实例。
request:仅适用于Web环境下的ApplicationContext,表示每一个HttpRequest生命周期内会有一个单独的实例,即每一个Http请求都会拥有一个单独的实例。
session:仅适用于Web环境下的ApplicationContext,表示每一个HttpSession生命周期内会有一个单独的实例,即每一个HttpSession下都会拥有一个单独的实例,即每一个用户都将拥有一个单独的实例。
globalSession:仅适用于Web环境下的ApplicationContext,一般来说是Portlet环境下。表示每一个全局的Http Session下都会拥有一个单独的实例。
application:仅适用于Web环境下的ApplicationContext,表示在ServletContext生命周期内会拥有一个单独的实例,即在整个ServletContext环境下只会拥有一个实例。

11. Spring Bean的装配方式(基于XML方式装配、基于注解方式装配)

12. 最常见的Spring的注解

1.@Controller
在控制层使用,标识该类是 Spring MVC controller 处理器,用来创建处理 http 请求的对象。

2.@Service
在业务逻辑层使用,用于标注业务层组件。

3.@Repository
在数据访问层使用,用于标注数据访问组件,即 DAO 组件。

4.@Component
泛指组件,当组件不好归类的时候,我们可以使用这个注解进行标注。

5.@Autowired
把配置好的 bean 拿来用,完成属性、方法的组装,它可以对类成员变量、方法及构造函数进行标注,完成自动装配的工作。

6.@Resource
它的作用相当于 @Autowired 注解的作用。

7.@Bean
相当于 XML 中的,放在方法的上面,而不是类,意思是产生一个 Bean,并交给 Spring 的容器管理。

8.@Configuration
声明当前类为配置类,相当于 xml 形式的 Spring 配置。

9.@ComponentScan
用于对 Component 组件进行扫描。

10.@Value
为对应的属性注入值。

11.@RunWith
运行器,Spring 中通常用于对 Junit 的支持。

12.@RequestMapping
用于映射 Web 请求,包括访问路径和参数。

13.@ResponseBody
支持将返回值放在 response 内,而不是一个页面,通常用户返回 json 数据。

14.@RestController
用于标注控制层组件,包含 @Controller 和 @ResponseBody。

15.@RequestParam
用于将请求参数区数据映射到功能处理方法的参数上。

16.@Scope
用来配置 Spring Bean 的作用域,它标识 Bean 的作用域。

17.@Qualifier
当你创建多个具有相同类型的 bean 时,并且想要用一个属性只为它们其中的一个进行装配,在这种情况下,你可以使用 @Qualifier 注解和 @Autowired 注解通过指定哪一个真正的 bean 将会被装配来消除混乱。

18.@Transactional
通过这个注解可以声明事务,可以添加在类上或者方法上。

19.@Aspect
声明一个切面(类上)使用 @After、@Before、@Around 定义通知(advice),可直接将拦截规则(切点)作为参数。

20.@PointCut
声明切点,在 java 配置类中使用。

21.@After
在方法执行之后执行(方法上)。

22.@Before
在方法执行之前执行(方法上)。

23.@Around
在方法执行之前与之后执行(方法上)。

13. Spring自动装配方式

在Spring中,支持五种自动装配模式,可以用来指导Spring容器用自动装配方式来进行依赖注入

(1)no

  • 这是Spring框架的默认设置,在该设置下自动装配是关闭的,开发者需要自行在bean定义中用标签明确的设置依赖关系。
<!-- no – 缺省情况下,自动配置是通过“ref”属性手动设定 -->
	<bean id="person" class="org.spring.autowring.Person">
		<property name="ability" ref="ability"></property>
	</bean>
	<bean id="ability" class="org.spring.autowring.Ability">
		<property name="skill" value="Java Programming"></property>
	</bean>

(2)byName

  • 根据Bean的名字进行自动装配。当向一个bean中自动装配一个属性时,容器将根据bean的名称自动在在配置文件中查询一个匹配的bean。如果找到的话,就装配这个属性,如果没找到的话就报错。
<!-- Auto-Wiring "byName" 按属性名称自动装配 -->
	<bean id="person" class="org.spring.autowring.Person" autowire="byName"/> 
    <bean id="ability" class="org.spring.autowring.Ability"> 
        <property name="skill" value="Java Programming"></property> 
   </bean>

(3)byType

  • 根据Bean的类型进行自动装配。当向一个bean中自动装配一个属性时,容器将根据bean的类型自动在在配置文件中查询一个匹配的bean。如果找到的话,就装配这个属性,如果没找到的话就报错。
<!-- Auto-Wiring "byType" 按属性名称自动装配 -->
    <bean id="person" class="org.spring.autowring.Person" autowire="byType"/>
    <bean id="ability" class="org.spring.autowring.Ability">
        <property name="skill" value="Java Programming"></property>
    </bean>

(4)constructor

  • 类似于byType,不过是应用于构造器的参数,如果正好有一个Bean与构造器的参数类型相同则可以自动装配,否则会导致错误。
<!-- constructor – 在构造函数参数的byType方式。 -->
    <!-- 构造方法的参数 -->
    <bean id="person" class="org.spring.autowring.Person">
        <constructor-arg>
            <ref bean="ability"></ref>
        </constructor-arg>
    </bean>
    <bean id="ability" class="org.spring.autowring.Ability">
        <property name="skill" value="Java Programming"></property>
    </bean>

(5)autodetect

  • 该模式自动探测使用构造器自动装配或者byType自动装配。首先,首先会尝试找合适的带参数的构造器,如果找到的话就是用构造器自动装配,如果在bean内部没有找到相应的构造器或者是无参构造器,容器就会自动选择byTpe的自动装配方式。
<bean id="HelloWorld" class="com.example.demo.test.HelloWorld"
		autowire="autodetect">
		<property name="msg">
			<value>HelloWorld</value>
		</property>
	</bean>
	<bean id="date" class="java.util.Date"></bean>

14. 什么是AOP?

        全称是 Aspect Oriented Programming 即:面向切面编程。是OOP的延续,也是Spring框架中的一个重要内容,是函数式编程的一种衍生泛型。简单的说他就是把我们程序重复的代码抽取出来,在需要执行的时候使用动态代理技术在不修改源码的基础上,对我们的已有方法进行增强。

15. AOP的术语

Joinpoint(连接点):
所谓连接点是指那些被拦截到的点。在 spring 中,这些点指的是方法,因为 spring 只支持方法类型的
连接点。

Pointcut(切入点):
所谓切入点是指我们要对哪些 Joinpoint 进行拦截的定义。

Advice(通知/增强):
所谓通知是指拦截到 Joinpoint 之后所要做的事情就是通知。
通知的类型:前置通知,后置通知,异常通知,最终通知,环绕通知。

Introduction(引介):
引介是一种特殊的通知在不修改类代码的前提下, Introduction 可以在运行期为类动态地添加一些方
法或 Field。

Target(目标对象):
代理的目标对象。

Weaving(织入):
是指把增强应用到目标对象来创建新的代理对象的过程。
spring 采用动态代理织入,而 AspectJ 采用编译期织入和类装载期织入。

Proxy(代理):
一个类被 AOP 织入增强后,就产生一个结果代理类。

Aspect(切面):
是切入点和通知(引介)的结合。

16. 了解 AOP动态代理 (JDK动态代理、CGlib动态代理 他们的区别是什么)

(1)JDK动态代理只能对实现了接口的类生成代理,而不能针对类
(2)CGLIB是针对类实现代理,主要是对指定的类生成一个子类,覆盖其中的方法
因为是继承,所以该类或方法最好不要声明成final

JDK动态代理只提供接口的代理,不支持类的代理。核心InvocationHandler接口和Proxy类,InvocationHandler 通过invoke()方法反射来调用目标类中的代码,动态地将横切逻辑和业务编织在一起;接着,Proxy利用 InvocationHandler动态创建一个符合某一接口的的实例, 生成目标类的代理对象。
如果代理类没有实现 InvocationHandler 接口,那么Spring AOP会选择使用CGLIB来动态代理目标类。CGLIB(Code Generation Library),是一个代码生成的类库,可以在运行时动态的生成指定类的一个子类对象,并覆盖其中特定方法并添加增强代码,从而实现AOP。CGLIB是通过继承的方式做的动态代理,因此如果某个类被标记为final,那么它是无法使用CGLIB做动态代理的。

17. SpringAOP的通知类型

        1.前置通知 Before advice:在连接点前面执行,前置通知不会影响连接点的执行,除非此处抛出异常
        2.后置通知 After returning advice:在连接点正常执行完成后执行,如果连接点抛出异常,则不会执行
        3.异常通知 After throwing advice:在连接点抛出异常后执行
        4.最终通知 After (finally) advice:在连接点执行完成后执行,不管是正常执行完成,还是抛出异常,都会执行返回通知中的内容
        5.环绕通知 Around advice:环绕通知围绕在连接点前后,能在方法调用前后自定义一些操作,还需要负责决定是继续处理 join point (调用 ProceedingJoinPoint 的 proceed 方法)还是中断执行

18. 了解AOP切点表达式的写法

内容过多,具体可看此链接内容

(34条消息) 第15章-Spring AOP切点表达式(Pointcut)详解_码匠_CodeArtist的博客-CSDN博客

19. Spring事务管理 (什么是事务,事务特性,Spring管理事务的2种方式,事务的传播行为)

        在 Spring 框架中事务管理有两种方式:一种是传统的编程式事务管理,即通过编写代码实现的事务管理;另一种是基于 AOP 技术实现的声明式事务管理。由于在 Spring 框架中,编程式事务管理很少使用,所以我们只对 Spring 的声明式事务管理进行详细讲解。
Spring 的声明式事务管理在底层采用了 AOP 技术,其最大的优点在于无须通过编程的方式管理事务,只需要在配置文件中进行相关的规则声明,就可以将事务规则应用到业务逻辑中。

Spring 实现声明式事务管理主要有两种方式:

基于 XML 文件方式的声明式事务管理。
通过 Annotation 注解方式的事务管理。

事务一般是指数据库事务,是指作为一个程序执行单元执行的一系列操作,要么完全执行,要么完全不执行。事务就是判断以结果为导向的标准。
(1)原子性(atomicity)
原子性就是一个不可分割的工作单位。简单地说,就是在日常工作中,老板交给你做一件事情,然后你做到半路做不动了或者说做到最后没做完,那么这个老板就会认为你什么都没有做,做一半的东西不算数,因为老板提前告诉你他只看结果,所以最终没有看到结果,不算是做了。通俗的说就是要么全部完成,要么全部没完成回到起始的地方。
(2)一致性(consistency)
一致性就是事务必须是使一个一致性状态变成另一个一致性状态。比如说我们写一个电商项目,一个用户买商品下单的时候一般都是两步,一步就是选择商品下单,第二步就是把商品在数据库中扣除库存,如果我们买了十件商品,那么数据库中扣除了不是十件商品,或者三件或者四件或者别的,那么这就不满足一致性。
(3)隔离性(isolation)
隔离性就是一个事物的执行不能被另一个事务干扰。还是说我们的电商,一个用户下单之后在减库存的过程中,另一个用户也下单了,他也要减库存,在这个用户还没有减的时候,另一个用户给减掉了,那么库存没有了,这就是事务被另一个事务干扰了。
(4)持久性(durability)
持久性就是一个事务一旦被提交,它对数据库中数据的改变就应该是永久性的。就是说我们在执行一个sql语句之后还没有被提交,这是系统宕机了,那么数据并没有被保存下来,但是当我们把数据提交之后,存在了文件中,这时不管怎么样我们的数据都不会遭到破坏。

事务传播行为是指:多个含有事务的方法相互调用时,事务如何在这些方法间传播。
在这里插入图片描述

 

  • 3
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值