Spring總結與感悟

Spring重點總結

依賴注入(DI)

set方式注入【重點】

<?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">

    <bean id="address" class="pojo.Address">
        <property name="address" value="address你好" />
    </bean>

    <bean id="student" class="pojo.Student">
        <!--第一種,普通值注入 -->
        <property name="name" value="name你好" />
        <!--第二種,ref注入 -->
        <property name="address" ref="address" />

        <!--數組注入 -->
        <property name="books">
            <array>
                <value>三國</value>
                <value>西遊</value>
                <value>水滸</value>
            </array>
        </property>

        <!--list列表注入 -->
        <property name="hobbies">
            <list>
                <value></value>
                <value></value>
                <value>rap</value>
                <value>籃球</value>
            </list>
        </property>

        <!--map鍵值對注入 -->
        <property name="card">
            <map>
                <entry key="username" value="root" />
                <entry key="password" value="root" />
            </map>
        </property>

        <!--set(可去重)注入 -->
        <property name="game">
            <set>
                <value>wangzhe</value>
                <value>lol</value>
                <value>galname</value>
            </set>
        </property>

        <!--空指針null注入 -->
        <property name="wife">
            <null></null>
        </property>

        <!--properties常量注入 -->
        <property name="infor">
            <props>
                <prop key="id">20200802</prop>
                <prop key="name">cbh</prop>
            </props>
        </property>
    </bean>
</beans>

使用p和c命名空間須要導入xml約束

<!--p命名空間注入/set注入,能夠直接注入屬性的值-》property-->
    <bean id="user" class="pojo.User" p:name="cxk" p:id="20" >
    </bean>

    <!--c命名空間,經過構造器注入,須要寫入有參和無參構造方法-》construct-args-->
    <bean id="user2" class="pojo.User" c:name="cbh" c:id="22"></bean>

Bean的自動裝配

Spring會在上下文自動尋找,並自動給bean裝配屬性java

在Spring中有三種裝配的方式web

 

  1. 在xml中顯示配置spring

  2. 在java中顯示配置express

  3. 隱式的自動裝配bean 【重要】apache

 

  1. byType自動裝配:byType會自動查找,和本身對象set方法參數的類型相同的bean編程

    保證全部的class惟一(類爲全局惟一)數組

  2. byName自動裝配:byName會自動查找,和本身對象set對應的值對應的idspring-mvc

    保證全部id惟一,而且和set注入的值一致緩存

實例:安全

People類

package com.xlf.pojo; import org.apache.ibatis.annotations.CacheNamespace; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import javax.annotation.Resource; public class People { @Resource private Cat cat; @Resource // @Qualifier(value = "dog222")
    private Dog dog; private String name; @Override public String toString() { return "People{" +
                "cat=" + cat +
                ", dog=" + dog +
                ", name='" + name + '\'' +
                '}'; } public Cat getCat() { return cat; } public void setCat(Cat cat) { this.cat = cat; } public Dog getDog() { return dog; } public void setDog(Dog dog) { this.dog = dog; } public String getName() { return name; } public void setName(String name) { this.name = name; } }

xml配置 -> byType 自動裝配

 <bean id="cat" class="pojo.Cat"/>
    <bean id="dog" class="pojo.Dog"/>
    
    <!--byType會在容器自動查找,和本身對象屬性相同的bean 例如,Dog dog; 那麼就會查找pojo的Dog類,再進行自動裝配 -->
    <bean id="people" class="pojo.People" autowire="byType">
        <property name="name" value="xlf"></property>
    </bean>

xml配置 -> byName 自動裝配

<bean id="cat" class="pojo.Cat"/>
<bean id="dog" class="pojo.Dog"/>
<!--byname會在容器自動查找,和本身對象set方法的set後面的值對應的id 例如:setDog(),取set後面的字符做爲id,則要id = dog 才能夠進行自動裝配 -->
<bean id="people" class="pojo.People" autowire="byName">
    <property name="name" value="xlf"></property>
</bean>

使用註解實現自動裝配

1.導入context約束:xmlns:context="http://www.springframework.org/schema/context"

2.配置註解的支持:< context:annotation-config/>

@Autowired:默認是byType方式,若是匹配不上,就會byName

public class People { @Autowired private Cat cat; @Autowired private Dog dog; private String name; }

@Resource:默認是byName方式,若是匹配不上,就會byType

public class People { Resource(name="cat") private Cat cat; Resource(name="dog") private Dog dog; private String name; }

@Nullable:字段標記了這個註解,說明該字段能夠爲空

區別:

@Resource和@Autowired的區別:

  • 都是用來自動裝配的,均可以放在屬性字段上

  • @Autowired經過byType的方式實現,並且必需要求這個對象存在!【經常使用】

  • @Resource默認經過byname的方式實現,若是找不到名字,則經過byType實現!若是兩個都找不到的狀況下,就報錯!【經常使用】

  • 執行順序不一樣:@Autowired經過byType的方式實現。@Resource默認經過byname的方式實現

 

 

使用註解開發

使用註解須要導入contex的約束

<?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 https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">

    <context:annotation-config/>

</beans>

bean

<!--指定要掃描的包,這個包下面的註解纔會生效 別隻掃一個com.kuang.pojo包--> 
<context:component-scan base-package="com.kuang"/> 
<context:annotation-config/>
//@Component 組件 //等價於<bean id="user" classs"pojo.User"/> 
@Component public class User { public String name ="xlf"; }

屬性如何注入@value

@Component public class User { //至關於<property name="name" value="xlf"/> 
    @value("xlf") public String name; //也能夠放在set方法上面 //@value("xlf")
    public void setName(String name) { this.name = name; } }

做用域@scope

原型模式prototype,單例模式singleton

 

scope("prototype")至關於<bean scope="prototype"></bean>

AOP

AOP在Spring中的使用

提供聲明式事務,容許用戶自定義切面

 

  • 橫切關注點:跨越應用程序多個模塊的方法或功能。便是,與咱們業務邏輯無關的,可是咱們須要關注的部分,就是橫切關注點。如日誌,安全,緩存,事務等等…

  • 切面(Aspect):橫切關注點 被模塊化的特殊對象。即,它是一個類。(Log類)

  • 通知(Advice):切面必需要完成的工做。即,它是類中的一個方法。(Log類中的方法)

  • 目標(Target):被通知對象。(生成的代理類)

  • 代理(Proxy):向目標對象應用通知以後建立的對象。(生成的代理類)

  • 切入點(PointCut):切面通知執行的」地點」的定義。(最後兩點:在哪一個地方執行,好比:method.invoke())

  • 鏈接點(JointPoint):與切入點匹配的執行點。

 

使用Spring實現AOP

導入jar包

<dependency>
    <groupId>org.aspectj</groupId>
    <artifactId>aspectjweaver</artifactId>
    <version>1.9.4</version>
</dependency>

自定義類實現AOP

<?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:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd">

   <!--註冊bean-->
   <bean id="userservice" class="service.UserServiceImpl"/>
   <bean id="log" class="log.Log"/>
   <bean id="afterLog" class="log.AfterLog"/>
   <!-- 方式二,自定義 -->
   <bean id="diy" class="diy.DiyPointcut"/>
   <aop:config>
       <!--自定義切面-->
       <aop:aspect ref="diy">
           <!--切入點-->
           <aop:pointcut id="point" expression="execution(* service.UserServiceImpl.*(..))"/>
           <aop:before method="before" pointcut-ref="point"/>
           <aop:after method="after" pointcut-ref="point"/>
       </aop:aspect>
   </aop:config>

</beans>

使用註解實現

<?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:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd">
    
    <!-- 註冊 -->
    <bean id="userservice" class="service.UserServiceImpl"/>
    <!--方式三,使用註解實現-->
    <bean id="diyAnnotation" class="diy.DiyAnnotation"></bean>
    
    <!-- 開啓自動代理 實現方式:默認JDK (proxy-targer-class="fasle") cgbin (proxy-targer-class="true")-->
    <aop:aspectj-autoproxy/>
    
</beans>

  

package diy; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.After; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Before; @Aspect //標註這個類是一個切面
public class DiyAnnotation { @Before("execution(* service.UserServiceImpl.*(..))") public void before(){ System.out.println("=====方法執行前====="); } @After("execution(* service.UserServiceImpl.*(..))") public void after(){ System.out.println("=====方法執行後====="); } //在環繞加強中,咱們能夠給地暖管一個參數,表明咱們要獲取切入的點
    @Around("execution(* service.UserServiceImpl.*(..))") public void around(ProceedingJoinPoint joinPoint) throws Throwable { System.out.println("環繞前"); Object proceed = joinPoint.proceed(); System.out.println("環繞後"); } }

測試:

public class MyTest5 { public static void main(String[] args) { ApplicationContext context = new ClassPathXmlApplicationContext("applicationContext.xml"); //注意:動態代理代理的是接口
        UserService userService = (UserService) context.getBean("userservice"); userService.add(); } }

輸出:

 

 

聲明式事務

事務的ACID原則:一、原子性二、隔離性三、一致性四、持久性

Spring中的事務管理

 

  • 聲明式事務:AOP

  • 編程式事務:須要再代碼中,進行事務管理

<!--聲明式事務-->
    <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
        <constructor-arg ref="datasource" />
    </bean>

    <!--結合aop實現事務織入-->
    <!--配置事務的通知類-->
    <tx:advice id="txAdvice" transaction-manager="transactionManager">
        <!--給哪些方法配置事務-->
        <!--新東西:配置事務的傳播特性 propagation-->
        <tx:attributes>
            <tx:method name="add" propagation="REQUIRED"/>
            <tx:method name="delete" propagation="REQUIRED"/>
            <tx:method name="update" propagation="REQUIRED"/>
            <tx:method name="query" read-only="true"/>
            <!-- *號包含上面4個方法: <tx:method name="*" propagation="REQUIRED"/> -->
        </tx:attributes>
    </tx:advice>

    <!--配置事務切入-->
    <aop:config>
        <aop:pointcut id="txpointcut" expression="execution(* mapper.*.*(..))"/>
        <aop:advisor advice-ref="txAdvice" pointcut-ref="txpointcut"/>
    </aop:config>

REQUIRED--支持當前事務,若是當前沒有事務,就新建一個事務。這是最多見的選擇。

NESTED--若是當前存在事務,則在嵌套事務內執行。若是當前沒有事務,則進行與REQUIRED相似的操做。

聲明事務的本質是:當一個事務發生錯誤時,能夠及時的回滾,而不是一部分執行,錯誤的不執行。

 

感悟

spring的重點三大部分:

 

  • 控制反轉(IoC)

  • 面向切面編程(AOP)

  • 事務處理

總結一句話:Spring就是一個輕量級的控制反轉(IoC)和麪向切面編程(AOP)的框架!

目前,針對一個剛剛入門spring的小白,只是大概地學習了spring,還有不少的不足,接下來要進行spring-mvc的學習,但願在接下來的學習能夠更深刻的理解spring

 

 

<?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">
<bean id="address" class="pojo.Address"><property name="address" value="address你好" /></bean>
<bean id="student" class="pojo.Student"><!--第一種,普通值注入 --><property name="name" value="name你好" /><!--第二種,ref注入 --><property name="address" ref="address" />
<!--數組注入 --><property name="books"><array><value>三國</value><value>西遊</value><value>水滸</value></array></property>
<!--list列表注入 --><property name="hobbies"><list><value>唱</value><value>跳</value><value>rap</value><value>籃球</value></list></property>
<!--map鍵值對注入 --><property name="card"><map><entry key="username" value="root" /><entry key="password" value="root" /></map></property>
<!--set(可去重)注入 --><property name="game"><set><value>wangzhe</value><value>lol</value><value>galname</value></set></property>
<!--空指針null注入 --><property name="wife"><null></null></property>
<!--properties常量注入 --><property name="infor"><props><prop key="id">20200802</prop><prop key="name">cbh</prop></props></property></bean></beans>

相關文章
相關標籤/搜索