SpEL表达式使用记录

SpEL表达式的首要目标是通过计算获得某个值。在计算这个数值的过程中,会使用到其他的值并会对这些值进行操作。最简单的SpEL求值或许是对字面值、Bean的属性或者某个类的常量进行求值。

SpEL表达式使用#{}作为取值运算符。

一、字面值

1、最简单的SpEL表达式或许仅包含一个字面值:

<property name="count" value="#{5}"/>

2、非SpEL表达式的值混用:

<property name="message" value="Thevalueis#{5}"/>

3、浮点型数字一样可以出现在SpEL表达式中:

<property name="frequency" value="#{89.7}"/>

4、String类型的字面值可以使用单引号或双引号作为字符串的界定符。将一个String类型的字面值装配到Bean的一个属性中:

<property name="name" value="#{'Chuck'}"/>
<property name='name' value='#{"Chuck"}'/>

5、装配布尔型的true和false:

<property name="enabled" value="#{false}"/>

二、引用bean、properties和方法

1、在SpEL表达式中使用BeanID将一个Bean装配到另一个Bean的属性中:

<property name="instrument" value="#{saxophone}"/>

等效于:

<property name="instrument" ref="saxophone"/>

2、将一个bean的属性装配到另一个bean的属性中:

<bean id="carl" class="com.springinaction.springidol.Instrumentalist">
    <property name="song" value="#{kenny.song}"/>
</bean>

通过这种方式装配carlBean的song属性,其实等价于执行下面的示例代码:

Instrumentalist carl=new Instrumentalist();
carl.setSong(kenny.getSong());

3、调用一个bean的方法,将其返回值装配到另一个bean属性中:

<property name="song" value="#{songSelector.selectSong()}"/>
<property name="song" value="#{songSelector.selectSong().toUpperCase()}"/>

在SpEL中避免抛出讨厌的空指针异常(NullPointerException)的方法是使用null-safe存取器:

<property name="song" value="#{songSelector.selectSong()?.toUpperCase()}"/>

现在我们使用?.运算符代替点(.)来访问toUpperCase()方法。在访问右边方法之前,该运算符会确保左边项的值不会为null。所以,如果selectSong()返回null值,SpEL不再尝试调用toUpperCase()方法。

三、操作类

在SpEL中,使用T()运算符会调用类作用域的方法和常量。例如,在SpEL中使用Java的Math类,我们可以像下面的示例这样使用T()运算符:T(java.lang.Math)

1、把PI的值装配到Bean的一个属性中:

<propert yname="multiplier" value="#{T(java.lang.Math).PI}"/>

2、使用T()运算符也可以调用静态方法,将一个随机数(在0到1之间)装配到Bean的一个属性中:

<property name="randomNumber" value="#{T(java.lang.Math).random()}"/>

四、进行基础数学运算

1、两个数字相加,可以像下面那样使用+运算符:

<property name="adjustedAmount" value="#{counter.total+42}"/>

2、-运算符执行减法运算:

<property name="adjustedAmount" value="#{counter.total-20}"/>

3、*运算符执行乘法运算:

<property name="circumference" value="#{2*T(java.lang.Math).PI*circle.radius}"/>

4、/运算符执行除法运算:

<property name="average" value="#{counter.total/counter.count}"/>

5、%运算符执行求余运算:

<property name="remainder" value="#{counter.total%counter.count}"/>

6、不同于Java,SpEL还提供了乘方运算,如下所示:

<property name="area" value="#{T(java.lang.Math).PI*circle.radius^2}"/>

7、特别提一下+运算符,它还可以执行字符串连接。如下所示:

<property name="fullName" value="#{performer.firstName+''+performer.lastName}"/>

五、比较值

1、比较两个值是否相等:

<propertyname="equal"value="#{counter.total==100}"/>

2、类似地,小于(<)和大于(>)运算符用于比较不同的值。而且SpEL还提供了大于等于(>=)和小于等于(<=)运算符。
不过,在Spring的XML配置文件中使用小于等于和大于等于符号时,会报错,这是因为这两个符号在XML中有特殊含义。当在XML中使用SpEL时,最好对这些运算符使用SpEL的文本替代方式(textualalternatives),如下所示:

<property name="hasCapacity" value="#{counter.total le 100000}"/>

在这里,le运算符代表小于等于。其他的文本型比较运算符如表2.6所示。

3、使用and运算符,如下所示:

<property name="largeCircle" value="#{shape.kind=='circle' and shape.perimeter gt 10000}"/>

4、布尔类型的表达式求反,有两种运算符可以选择:符号型的!或者文本型的not。使用!运算符,如下所示:

<property name="outOfStock" value="#{!product.available}"/>

与使用not运算符是等价的:

<property name="outOfStock" value="#{notproduct.available}"/>

六、条件表达式

1、用SpEL的三元运算符(?:):

<property name="instrument" value="#{songSelector.selectSong()=='JingleBells'?piano:saxophone}"/>

虽然以上配置可以正常工作,但这里kenny.song的引用重复了两次。SpEL提供了三元运算符的变体来简化表达式:

<property name="song" value="#{kenny.song?:'Greensleeves'}"/>

在以上示例中,如果kenny.song不为null,那么表达式的求值结果是ken-ny.song,否则就是“Greensleeves”。

2、SpEL的正则表达式

假设我们想判断一个字符串是否是有效的邮件地址。在这种场景下,我们可以使用matches运算符,如下所示:

<property name="validEmail" value="#{admin.email matches '[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\.com'}"/>

七、筛选集合

SpEL还可以从集合的成员中提取某些属性放到一个新的集合中

假设我们定义了一个City类,如下所示(因为篇幅原因我们删除了getter/setter方法):

package com.habuma.spel.cities;
public class City{
    private String name;
    private String state;
    private int population;
}

通过Spring的元素定义的一个City的List集合:

<util:list id="cities">
    <bean class="com.habuma.spel.cities.City" p:name="Chicago" p:state="IL" p:population="2853114"/>
    <bean class="com.habuma.spel.cities.City" p:name="Atlanta" p:state="GA" p:population="537958"/>
    <bean class="com.habuma.spel.cities.City" p:name="Dallas" p:state="TX" p:population="1279910"/>
    <bean class="com.habuma.spel.cities.City" p:name="Houston" p:state="TX" p:population="2242193"/>
    <bean class="com.habuma.spel.cities.City" p:name="Odessa" p:state="TX" p:population="90943"/>
    <bean class="com.habuma.spel.cities.City" p:name="ElPaso" p:state="TX" p:population="613190"/>
    <bean class="com.habuma.spel.cities.City" p:name="Jal" p:state="NM" p:population="1996"/>
    <bean class="com.habuma.spel.cities.City" p:name="LasCruces" p:state="NM" p:population="91865"/>
</util:list>

1、中括号([])运算符会始终通过索引访问集合中的成员。

从集合中提取一个成员,并将它装配到某个属性中:

<property name="chosenCity" value="#{cities[2]}"/>

假设你随机选择一个city:

<property name="chosenCity" value="#{cities[T(java.lang.Math).random()*cities.size()]}"/>

2、[]运算符同样可以用来获取java.util.Map集合中的成员,通过key获取:
假设City对象以其名字作为键放入Map集合中,获取键为Dallas的entry:

<propertyname="chosenCity"value="#{cities['Dallas']}"/>

3、[]运算符的另一种用法是从java.util.Properties集合中获取值

通过<util:properties>元素在Spring中加载一个properties配置文件,如下所示:

<util:properties id="settings" location="classpath:settings.properties"/>

使用SpEL从settings Bean中访问一个名为twitter.accessToken的属性,如下所示:

<property name="accessToken" value="#{settings['twitter.accessToken']}"/>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值