IOC和AOP扩展


上一篇我们学习了IOC和AOP的基本概念,现在我们来深入了解一下。

IOC扩展

上一篇中使用Spring通过 setter访问器实现了对属性的赋值,这种做法称为设值注入。除此之外,Spring还提供了通过多种方式实现依赖注入。

构造注入(通过构造函数注入数据)

通过构造方法的赋值能力,称为构造注入。
示例:
类:

package cn.bdqn.spring.IOC;

public class HelloSpring {
    public HelloSpring(){
        System.out.println("调用无参构造方法");
    }
    public HelloSpring(String who,String hello){
        System.out.println("调用带参构造方法");
        this.who=who;
        this.hello=hello;
    }
    //定义一个who属性,该属性的值通过Spring框架进行设置
    private String who;
    private String hello;
    public void print(){
        System.out.println(this.hello+this.who+"!");
    }
}

配置文件

    <!--使用构造注入-->
    <bean id="HelloSpring" class="cn.bdqn.spring.IOC.HelloSpring">
        <constructor-arg index="0" type="java.lang.String" value="Spring"/>
        <constructor-arg index="1" type="java.lang.String" value="Heelo"/>
    </bean>

解析
(1) 一个<constructor-arg>元素表示构造方法的一个参数,且使用时不区分顺序。

(2)有多个参数通过<constructor-arg>元素的index 属性可以指定该参数的位置索引,位置从0 开始。

(3)<constructor-arg>元素还提供了type 属性用来指定参数的类型,避免字符串和基本数据类型的混淆。
构造注入的时效性较好,在对象实例化时就得到所依赖的对象,便于在构造函数中(初始化对象的过程中)使用所依赖的对象,但是灵活性不足。设值注入的方式较灵活,但时效性不足,并且大量属性的setter方法增加了类的复杂性。Spring并不倾向或提倡哪种注入方式,大家根据应用场景灵活选择。

p命名空间实现属性注入

非常简单:导入P的命名空间xmlns:p=“http://www.springframework.org/schema/p”
P命名空间的特点是使用元素的属性而非子节点的形式配置Bean的属性,从而简化配置

    <bean id="HelloSpring" class="cn.bdqn.spring.IOC.HelloSpring" p:who="Spring" p:hello="Hello"/>

语法详讲
对于一个类中的普通类型字段,比如String、int什么的,我们可以直接p:属性名="值"的方式进行赋值,这样就不用写子元素了,大大简化了配置。对于复杂类型,比如引用了其他的实体类(Bean组件),通过p:属性名-ref="所引用Bean的id"的方式进行赋值。

构造注入和设值注入对比

在这里插入图片描述

注入不同参数

在使用IOC时有时要注入一些特别的数据该怎么办

带有特殊符号的值

属性值中包含了XML中的特殊字符(&、<、>等),则注入时需要进行处理。可使用<![CDATA[特殊符号]]>进行标记,也可将特殊字符进行转义引用。
XML预定的实体引用:

符号实体引用
<&lt;
>&gt;
$&amp;
&apos;
"&quot;

在这里发现CSDN中这些实体引用代表的也是这些特殊符号,逼的我不得不用代码形式标记起来。

注入集合类型的属性

非常简单,注入什么类型使用什么标签:

 <property name="list">
            <list>
                <value>1</value>
                <value>2</value>
            </list>
        </property>
        <property name="set">
            <set>
                <value>1</value>
                <value>2</value>
                <value>3</value>
            </set>
        </property>
        <property name="map">
            <map>
                <entry key="k1" value="v1"/>
                <entry key="k2" value="v2"/>
            </map>
        </property>

注入null和空字符串值

注入null:

   <property name="who">
   			<null/>
   	</property>

注入空字符串:

 <property name="who" value=""/>
 或
  <property name="who" >
  		<value></value>
  </property>

AOP扩展

环绕增强

将前置、后置、最终、异常这些增强结合到一起使用,还能控制返回值参数等,甚至控制目标方法是否执行。
增强类

    //环绕增强:最强增强、控制方法是否运行,控制方法返回值、参数
    public Object around(ProceedingJoinPoint pjp){
        Object result=null;
        try{
            System.out.println("前置增强");
            Object[] args=pjp.getArgs();//获得参数
            args[0]="wsj";//设置参数
            result =  pjp.proceed(args);//执行目标方法并获得返回值
            System.out.println("后置增强");
        }catch (Throwable e){
            System.out.println("异常增强");
        }finally {
            System.out.println("最终增强");
        }
        return result;//控制返回值
    }

配置文件

 <aop:config>
        <!--切入点-->
        <!--告诉Spring在哪切入 expression(连接点)告诉Spring连接谁-->
        <aop:pointcut id="pc" expression="execution(public int addUser(..))"/>
        <!--切面,告诉Spring增强谁(织入增强处理)-->
        <aop:aspect ref="UserServiceLog">
           <!-- &lt;!&ndash;前置增强,method告诉Spring前置增强的方法是哪个,pointcut-ref引入切入点,告诉Spring切入谁(增强谁)&ndash;&gt;
            <aop:before method="before" pointcut-ref="pc"></aop:before>
            &lt;!&ndash;returning注入目标方法的返回值&ndash;&gt;
            <aop:after-returning method="afterReturning" pointcut-ref="pc" returning="result"></aop:after-returning>
            <aop:after method="after" pointcut-ref="pc"/>
            <aop:after-throwing method="afterThrowing" pointcut-ref="pc" throwing="e"/>-->
            <aop:around method="around" pointcut-ref="pc"/>
        </aop:aspect>
    </aop:config>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值