最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Spring中SpEL表達(dá)式的使用全解

 更新時間:2024年04月09日 09:42:11   作者:禿了也弱了。  
SpEL是Spring框架中用于表達(dá)式語言的一種方式,本文主要介紹了Spring中SpEL表達(dá)式的使用全解,文中通過示例代碼介紹的非常詳細(xì),需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

一、概述

1、什么是SpEL

SpEL(Spring Expression Language)是Spring框架中用于表達(dá)式語言的一種方式。它類似于其他編程語言中的表達(dá)式語言,用于在運行時計算值或執(zhí)行特定任務(wù)。

SpEL提供了一種簡單且強大的方式來訪問和操作對象的屬性、調(diào)用對象的方法,以及實現(xiàn)運算、條件判斷等操作。它可以被用于XML和注解配置中,可以用于許多Spring框架中的特性,如依賴注入、AOP、配置文件等。

SpEL表達(dá)式可以在字符串中進(jìn)行定義,使用特殊的語法和符號來表示特定的操作。例如,可以使用${expression}來表示一個SpEL表達(dá)式,其中expression是具體的SpEL語句。

SpEL支持各種操作和函數(shù),包括算術(shù)運算、邏輯運算、條件判斷、正則表達(dá)式匹配、集合操作等。它還支持訪問上下文中的變量和參數(shù),以及調(diào)用對象的方法。

2、SpEL能做什么

SpEL表達(dá)式具有廣泛的功能,以下是一些SpEL表達(dá)式可以做的事情:

  • 訪問對象屬性:SpEL表達(dá)式可以通過對象引用來訪問對象的屬性,例如${object.property}。
  • 調(diào)用方法:SpEL表達(dá)式可以調(diào)用對象的方法,例如${object.method()}。
  • 進(jìn)行算術(shù)運算:SpEL表達(dá)式支持各種算術(shù)運算符,如加法、減法、乘法和除法。
  • 進(jìn)行邏輯運算:SpEL表達(dá)式支持邏輯運算符,如與、或、非等。
  • 進(jìn)行條件判斷:SpEL表達(dá)式可以進(jìn)行條件判斷,例如通過if語句判斷條件,并執(zhí)行相應(yīng)的操作。
  • 訪問集合元素和屬性:SpEL表達(dá)式可以通過索引或鍵來訪問集合中的元素或?qū)ο蟮膶傩浴?/li>
  • 執(zhí)行正則表達(dá)式匹配:SpEL表達(dá)式可以執(zhí)行正則表達(dá)式匹配,并返回匹配結(jié)果。
  • 訪問上下文變量和參數(shù):SpEL表達(dá)式可以訪問上下文中的變量和方法參數(shù)。
  • 進(jìn)行類型轉(zhuǎn)換:SpEL表達(dá)式可以進(jìn)行類型轉(zhuǎn)換操作,將一個對象轉(zhuǎn)換為另一種類型。
  • 支持特殊操作符:SpEL表達(dá)式支持一些特殊的操作符,如Elvis操作符(?:)、安全導(dǎo)航操作符(?.)等。

總的來說,SpEL表達(dá)式可以用于在運行時計算值、執(zhí)行任務(wù)和操作對象,提供了靈活且強大的表達(dá)能力,廣泛應(yīng)用于Spring框架中的各種功能和配置中。

二、SpEL表達(dá)式使用

0、用到的類

public class PlaceOfBirth {

    private String city;
    private String country;

    public PlaceOfBirth(String city) {
        this.city=city;
    }

    public PlaceOfBirth(String city, String country) {
        this(city);
        this.country = country;
    }

    public String getCity() {
        return city;
    }

    public void setCity(String s) {
        this.city = s;
    }

    public String getCountry() {
        return country;
    }

    public void setCountry(String country) {
        this.country = country;
    }

}
import java.util.*;

public class Society {

    private String name;

    public static String Advisors = "advisors";
    public static String President = "president";

    private List<Inventor> members = new ArrayList<Inventor>();
    private Map officers = new HashMap();

    public List getMembers() {
        return members;
    }

    public Map getOfficers() {
        return officers;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public boolean isMember(String name) {
        for (Inventor inventor : members) {
            if (inventor.getName().equals(name)) {
                return true;
            }
        }
        return false;
    }

}
import java.util.Date;
import java.util.GregorianCalendar;

public class Inventor {

    private String name;
    private String nationality;
    private String[] inventions;
    private Date birthdate;
    private PlaceOfBirth placeOfBirth;

    public Inventor(String name, String nationality) {
        GregorianCalendar c= new GregorianCalendar();
        this.name = name;
        this.nationality = nationality;
        this.birthdate = c.getTime();
    }

    public Inventor(String name, Date birthdate, String nationality) {
        this.name = name;
        this.nationality = nationality;
        this.birthdate = birthdate;
    }

    public Inventor() {
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getNationality() {
        return nationality;
    }

    public void setNationality(String nationality) {
        this.nationality = nationality;
    }

    public Date getBirthdate() {
        return birthdate;
    }

    public void setBirthdate(Date birthdate) {
        this.birthdate = birthdate;
    }

    public PlaceOfBirth getPlaceOfBirth() {
        return placeOfBirth;
    }

    public void setPlaceOfBirth(PlaceOfBirth placeOfBirth) {
        this.placeOfBirth = placeOfBirth;
    }

    public void setInventions(String[] inventions) {
        this.inventions = inventions;
    }

    public String[] getInventions() {
        return inventions;
    }
}

1、文字表達(dá)式

支持的文字表達(dá)式類型有字符串、數(shù)值(int、real、hex)、布爾和null。字符串由單引號分隔。若要將單引號本身放在字符串中,請使用兩個單引號字符。

通常來說,不會單純的定義一個簡單的文字表達(dá)式,而是通過方法調(diào)用等等復(fù)雜的操作,來完成一個功能:

// 定義Parser,可以定義全局的parser
ExpressionParser parser = new SpelExpressionParser();

// 獲取字符串 "Hello World"
String helloWorld = (String) parser.parseExpression("'Hello World'").getValue();
// double類型 6.0221415E23
double avogadrosNumber = (Double) parser.parseExpression("6.0221415E+23").getValue();

// int類型 2147483647
int maxValue = (Integer) parser.parseExpression("0x7FFFFFFF").getValue();
// true
boolean trueValue = (Boolean) parser.parseExpression("true").getValue();
// null
Object nullValue = parser.parseExpression("null").getValue();

2、屬性, 數(shù)組, List, Map,和 索引

(1)屬性操作

注意!屬性名的第一個字母不區(qū)分大小寫。

// 定義Parser,可以定義全局的parser
ExpressionParser parser = new SpelExpressionParser();

// 注意!屬性名的第一個字母不區(qū)分大小寫。 birthdate.year等效于Birthdate.Year
// 取出Inventor 中,birthdate屬性的year屬性
Inventor zhangsan = new Inventor("zhangsan", new Date(), "China");
// 定義StandardEvaluationContext ,傳入一個操作對象
StandardEvaluationContext zhangsanContext = new StandardEvaluationContext(zhangsan);
int year = (Integer) parser.parseExpression("birthdate.year + 1900").getValue(zhangsanContext);
System.out.println(year); // 2023

//取出Inventor的placeOfBirth的city屬性
PlaceOfBirth placeOfBirth = new PlaceOfBirth("長沙", "中國");
zhangsan.setPlaceOfBirth(placeOfBirth);
String city = (String) parser.parseExpression("placeOfBirth.City").getValue(zhangsanContext);
System.out.println(city); // 長沙

(2)數(shù)組和List

數(shù)組和List的內(nèi)容是通過使用方括號符號獲得的。

// 定義Parser,可以定義全局的parser
ExpressionParser parser = new SpelExpressionParser();

EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();

// 省略數(shù)據(jù)初始化

// 取出tesla對象的inventions 第四個數(shù)據(jù)
String invention = parser.parseExpression("inventions[3]").getValue(
        context, tesla, String.class);

// 取出ieee對象的第一個Member的name屬性
String name = parser.parseExpression("Members[0].Name").getValue(
        context, ieee, String.class);

// 取出ieee對象的第一個Member中的第七個Inventions
String invention = parser.parseExpression("Members[0].Inventions[6]").getValue(
        context, ieee, String.class);

(3)Map

Map操作是通過key來獲取的

// 取出societyContext的Officers中的key為president的值
Inventor pupin = parser.parseExpression("Officers['president']").getValue(
        societyContext, Inventor.class);


String city = parser.parseExpression("Officers['president'].PlaceOfBirth.City").getValue(
        societyContext, String.class);

// Officers中key為advisors的值取第一個
parser.parseExpression("Officers['advisors'][0].PlaceOfBirth.Country").setValue(
        societyContext, "Croatia");

3、內(nèi)嵌List

可以使用{}符號在表達(dá)式中直接表示List。{}本身意味著一個空列表。

// 定義Parser,可以定義全局的parser
ExpressionParser parser = new SpelExpressionParser();

EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();

// [1, 2, 3, 4]
List numbers = (List) parser.parseExpression("{1,2,3,4}").getValue(context);
System.out.println(numbers);

// 嵌套: [[a, b], [x, y]]
List listOfLists = (List) parser.parseExpression("{{'a','b'},{'x','y'}}").getValue(context);
System.out.println(listOfLists);

4、內(nèi)嵌Map

使用{key:value}符號在表達(dá)式中表示Map。{:}意味著空Map。

// 定義Parser,可以定義全局的parser
ExpressionParser parser = new SpelExpressionParser();

EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();

// {name=Nikola, dob=10-July-1856}
Map inventorInfo = (Map) parser.parseExpression("{name:'Nikola',dob:'10-July-1856'}").getValue(context);
System.out.println(inventorInfo);

// 嵌套:{name={first=Nikola, last=Tesla}, dob={day=10, month=July, year=1856}}
Map mapOfMaps = (Map) parser.parseExpression("{name:{first:'Nikola',last:'Tesla'},dob:{day:10,month:'July',year:1856}}").getValue(context);
System.out.println(mapOfMaps);

// List與Map可以嵌套使用,互相結(jié)合。
// 嵌套:[{name={first=Nikola, last=Tesla}}, {dob={day=10, month=July, year=1856}}]
List listOfMaps = (List) parser.parseExpression("{{name:{first:'Nikola',last:'Tesla'}},{dob:{day:10,month:'July',year:1856}}}").getValue(context);
System.out.println(listOfMaps);

5、構(gòu)建數(shù)組

多維數(shù)組不提供初始化方式。

// 定義Parser,可以定義全局的parser
ExpressionParser parser = new SpelExpressionParser();

EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();

int[] numbers1 = (int[]) parser.parseExpression("new int[4]").getValue(context);

// 數(shù)組并初始化
int[] numbers2 = (int[]) parser.parseExpression("new int[]{1,2,3}").getValue(context);

// 多維數(shù)組
int[][] numbers3 = (int[][]) parser.parseExpression("new int[4][5]").getValue(context);

6、調(diào)用類的方法

ExpressionParser parser = new SpelExpressionParser();

// 調(diào)用substring方法
String bc = parser.parseExpression("'abc'.substring(1, 3)").getValue(String.class);

// 調(diào)用societyContext中對象的isMember方法,并傳值。
StandardEvaluationContext societyContext = new StandardEvaluationContext(society);
boolean isMember = parser.parseExpression("isMember('Mihajlo Pupin')").getValue(
        societyContext, Boolean.class);

7、SpEL操作符

(1)標(biāo)準(zhǔn)運算符

使用標(biāo)準(zhǔn)運算符表示法支持關(guān)系運算符(等于、不等于、小于、小于或等于、大于和大于或等于)。

null不被視為任何東西(即不為零)。因此,任何其他值總是大于null (X > null總是為真),并且沒有任何其他值小于零(X < null總是為假)。

ExpressionParser parser = newSpelExpressionParser();

// evaluates to true
boolean trueValue = parser.parseExpression("2 == 2").getValue(Boolean.class);

// evaluates to false
boolean falseValue = parser.parseExpression("2 < -5.0").getValue(Boolean.class);

// evaluates to true
boolean trueValue = parser.parseExpression("'black' < 'block'").getValue(Boolean.class);

(2)instanceof 和 正則表達(dá)式的匹配操作符

使用基本類型時要小心,因為它們會立即被裝箱為包裝器類型,所以1 instanceof T(int)會計算為false,而1 instanceof T(Integer)會計算為true。

// evaluates to false
boolean falseValue = parser.parseExpression(
        "'xyz' instanceof T(Integer)").getValue(Boolean.class);

// evaluates to true
boolean trueValue = parser.parseExpression(
        "'5.00' matches '^-?\\d+(\\.\\d{2})?$'").getValue(Boolean.class);

//evaluates to false
boolean falseValue = parser.parseExpression(
        "'5.0067' matches '^-?\\d+(\\.\\d{2})?$'").getValue(Boolean.class);

(3)操作符的英文等價標(biāo)識

每個符號操作符也可以被指定為純字母的等價物。這避免了所使用的符號對于嵌入表達(dá)式的文檔類型具有特殊含義的問題(例如在XML文檔中)。所有文本操作符都不區(qū)分大小寫。對應(yīng)的文本是:
lt (<)
gt (>)
le (<=)
ge (>=)
eq (==)
ne (!=)
div (/)
mod (%)
not (!)

(4)邏輯運算符

SpEL支持以下邏輯運算符:and、or、not

// 結(jié)果: false
boolean falseValue = parser.parseExpression("true and false").getValue(Boolean.class);

// 調(diào)用方法并根據(jù)方法返回值判斷
String expression = "isMember('Nikola Tesla') and isMember('Mihajlo Pupin')";
boolean trueValue = parser.parseExpression(expression).getValue(societyContext, Boolean.class);

// -- OR --
boolean trueValue = parser.parseExpression("true or false").getValue(Boolean.class);

// 調(diào)用方法并根據(jù)方法返回值判斷
String expression = "isMember('Nikola Tesla') or isMember('Albert Einstein')";
boolean trueValue = parser.parseExpression(expression).getValue(societyContext, Boolean.class);

// -- NOT --
// 取反
boolean falseValue = parser.parseExpression("!true").getValue(Boolean.class);

// -- AND and NOT --
String expression = "isMember('Nikola Tesla') and !isMember('Mihajlo Pupin')";
boolean falseValue = parser.parseExpression(expression).getValue(societyContext, Boolean.class);

(5)數(shù)學(xué)運算符

可以對數(shù)字和字符串使用加法運算符
只能對數(shù)字使用減法、乘法和除法運算符
也可以使用模數(shù)(%)和指數(shù)冪(^)運算符。
強制執(zhí)行標(biāo)準(zhǔn)運算符優(yōu)先級。

// Addition
int two = parser.parseExpression("1 + 1").getValue(Integer.class);  // 2

String testString = parser.parseExpression(
        "'test' + ' ' + 'string'").getValue(String.class);  // 'test string'

// Subtraction
int four = parser.parseExpression("1 - -3").getValue(Integer.class);  // 4

double d = parser.parseExpression("1000.00 - 1e4").getValue(Double.class);  // -9000

// Multiplication
int six = parser.parseExpression("-2 * -3").getValue(Integer.class);  // 6

double twentyFour = parser.parseExpression("2.0 * 3e0 * 4").getValue(Double.class);  // 24.0

// Division
int minusTwo = parser.parseExpression("6 / -3").getValue(Integer.class);  // -2

double one = parser.parseExpression("8.0 / 4e0 / 2").getValue(Double.class);  // 1.0

// Modulus
int three = parser.parseExpression("7 % 4").getValue(Integer.class);  // 3

int one = parser.parseExpression("8 / 5 % 2").getValue(Integer.class);  // 1

// Operator precedence
int minusTwentyOne = parser.parseExpression("1+2-3*8").getValue(Integer.class);  // -21

(6)賦值運算符

若要給對象設(shè)置屬性,請使用賦值運算符(=)。這通常在對setValue的調(diào)用中完成,但也可以在對getValue的調(diào)用中完成。

// 定義Parser,可以定義全局的parser
ExpressionParser parser = new SpelExpressionParser();

Inventor inventor = new Inventor();
EvaluationContext context = SimpleEvaluationContext.forReadWriteDataBinding().build();

parser.parseExpression("Name").setValue(context, inventor, "Aleksandar Seovic");

System.out.println(inventor.getName()); // Aleksandar Seovic

// 或者這樣賦值
String aleks = parser.parseExpression(
        "Name = 'Aleksandar Seovic2'").getValue(context, inventor, String.class);
System.out.println(inventor.getName()); // Aleksandar Seovic2

8、獲取類的類型

可以使用特殊的T運算符來指定java.lang.Class的實例(類型)。靜態(tài)方法也是通過使用這個操作符來調(diào)用的。

StandardEvaluationContext使用TypeLocator來查找類型,StandardTypeLocator(可以替換)是基于對java.lang包的理解而構(gòu)建的。所以java.lang中類型的T()引用不需要使用全限定名,但是其他包中的類,必須使用全限定名。

ExpressionParser parser = new SpelExpressionParser();

Class dateClass = parser.parseExpression("T(java.util.Date)").getValue(Class.class);

Class stringClass = parser.parseExpression("T(String)").getValue(Class.class);

boolean trueValue = parser.parseExpression(
                "T(java.math.RoundingMode).CEILING < T(java.math.RoundingMode).FLOOR")
        .getValue(Boolean.class);

9、調(diào)用類構(gòu)造器

使用new運算符調(diào)用構(gòu)造函數(shù)。除了基本類型(int、float等)和String之外,所有類型都應(yīng)該使用完全限定的類名。

Inventor einstein = p.parseExpression(
        "new org.spring.samples.spel.inventor.Inventor('Albert Einstein', 'German')")
        .getValue(Inventor.class);

//創(chuàng)建一個新的Inventor,并且添加到members的list中
p.parseExpression(
        "Members.add(new org.spring.samples.spel.inventor.Inventor(
            'Albert Einstein', 'German'))").getValue(societyContext);

10、SpEL變量

(1)基本使用

可以使用#variableName語法在表達(dá)式中引用變量。通過在EvaluationContext實現(xiàn)上使用setVariable方法來設(shè)置變量

ExpressionParser parser = new SpelExpressionParser();

Inventor tesla = new Inventor("Nikola Tesla", "Serbian");

EvaluationContext context = SimpleEvaluationContext.forReadWriteDataBinding().build();
context.setVariable("newName", "Mike Tesla"); // 設(shè)置變量

// 獲取變量newName,并將其賦值給name屬性
parser.parseExpression("Name = #newName").getValue(context, tesla);
System.out.println(tesla.getName());  // "Mike Tesla"

(2)#this 和 #root變量

#this變量引用當(dāng)前的評估對象(根據(jù)該評估對象解析非限定引用)。

#root變量總是被定義并引用根上下文對象。雖然#this可能會隨著表達(dá)式的組成部分的計算而變化,但是#root總是指根。

// 創(chuàng)建一個Integer數(shù)組
List<Integer> primes = new ArrayList<Integer>();
primes.addAll(Arrays.asList(2,3,5,7,11,13,17));

// create parser and set variable 'primes' as the array of integers
ExpressionParser parser = new SpelExpressionParser();
EvaluationContext context = SimpleEvaluationContext.forReadWriteDataBinding().build();
context.setVariable("primes", primes);

//  numbers > 10 的 list 
// evaluates to [11, 13, 17]
List<Integer> primesGreaterThanTen = (List<Integer>) parser.parseExpression(
        "#primes.?[#this>10]").getValue(context);

System.out.println(primesGreaterThanTen);

11、調(diào)用類靜態(tài)方法

// 方法定義的方式
Method method = ...;

EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();
context.setVariable("myFunction", method);
// 準(zhǔn)備一個要調(diào)用的目標(biāo)方法
public class StringUtils {

    public static String reverseString(String input) {
        StringBuilder backwards = new StringBuilder(input.length());
        for (int i = 0; i < input.length(); i++) {
            backwards.append(input.charAt(input.length() - 1 - i));
        }
        return backwards.toString();
    }
}

// 調(diào)用目標(biāo)靜態(tài)方法
public static void main(String[] args) throws NoSuchMethodException {

	   ExpressionParser parser = new SpelExpressionParser();
	
	   EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();
	   // 獲取要調(diào)用的方法
	   context.setVariable("reverseString",
	           StringUtils.class.getDeclaredMethod("reverseString", String.class));
	
	   // 調(diào)用
	   String helloWorldReversed = parser.parseExpression(
	           "#reverseString('hello')").getValue(context, String.class);
}

12、Bean引用

如果已經(jīng)用bean解析器配置了評估上下文,則可以使用@符號從表達(dá)式中查找bean。

ExpressionParser parser = new SpelExpressionParser();
StandardEvaluationContext context = new StandardEvaluationContext();
context.setBeanResolver(new MyBeanResolver());

// 將調(diào)用MyBeanResolver 的 resolve(context,"something")
Object bean = parser.parseExpression("@something").getValue(context);
// 注意!MyBeanResolver 可以使用系統(tǒng)自帶的BeanFactoryResolver,寫成:
context.setBeanResolver(new BeanFactoryResolver(applicationContext));

// BeanFactoryResolver的resolve方法,就是通過Bean的名稱來獲取Bean:
@Override
public Object resolve(EvaluationContext context, String beanName) throws AccessException {
	try {
		return this.beanFactory.getBean(beanName);
	}
	catch (BeansException ex) {
		throw new AccessException("Could not resolve bean reference against BeanFactory", ex);
	}
}

要訪問工廠bean本身,應(yīng)該在bean名稱前加上&符號:

ExpressionParser parser = new SpelExpressionParser();
StandardEvaluationContext context = new StandardEvaluationContext();
context.setBeanResolver(new MyBeanResolver());

// 將調(diào)用MyBeanResolver 的 resolve(context,"something")
Object bean = parser.parseExpression("&foo").getValue(context);

13、三元運算符(If-Then-Else)

// 使用示例
String falseString = parser.parseExpression(
        "false ? 'trueExp' : 'falseExp'").getValue(String.class);
// name屬性設(shè)置值
parser.parseExpression("Name").setValue(societyContext, "IEEE");
// 設(shè)置變量
societyContext.setVariable("queryName", "Nikola Tesla");

// 三元運算符
expression = "isMember(#queryName)? #queryName + ' is a member of the ' " +
        "+ Name + ' Society' : #queryName + ' is not a member of the ' + Name + ' Society'";

String queryResultString = parser.parseExpression(expression)
        .getValue(societyContext, String.class);
// queryResultString = "Nikola Tesla is a member of the IEEE Society"

14、Elvis操作符

Elvis運算符是三元運算符語法的縮寫,用于Groovy語言中。使用三元運算符語法時,通常需要將一個變量重復(fù)兩次,如下例所示:

String name = "Elvis Presley";
String displayName = (name != null ? name : "Unknown");

可以使用Elvis運算符(因與Elvis的發(fā)型相似而得名)優(yōu)化。以下示例顯示了如何使用Elvis運算符:

ExpressionParser parser = new SpelExpressionParser();

String name = parser.parseExpression("name?:'Unknown'").getValue(String.class);
System.out.println(name);  // 'Unknown'

更復(fù)雜的實例:

ExpressionParser parser = new SpelExpressionParser();
EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();

Inventor tesla = new Inventor("Nikola Tesla", "Serbian");
String name = parser.parseExpression("Name?:'Elvis Presley'").getValue(context, tesla, String.class);
System.out.println(name);  // Nikola Tesla

tesla.setName(null);
name = parser.parseExpression("Name?:'Elvis Presley'").getValue(context, tesla, String.class);
System.out.println(name);  // Elvis Presley

15、安全導(dǎo)航操作員

安全導(dǎo)航操作符用于避免NullPointerException,來自Groovy語言。通常,當(dāng)引用一個對象時,可能需要在訪問該對象的方法或?qū)傩灾膀炞C它不為null。為了避免這種情況,安全導(dǎo)航運算符返回null,而不是引發(fā)異常。以下示例顯示了如何使用安全導(dǎo)航運算符:

ExpressionParser parser = new SpelExpressionParser();
EvaluationContext context = SimpleEvaluationContext.forReadOnlyDataBinding().build();

Inventor tesla = new Inventor("Nikola Tesla", "Serbian");
tesla.setPlaceOfBirth(new PlaceOfBirth("Smiljan"));

String city = parser.parseExpression("PlaceOfBirth?.City").getValue(context, tesla, String.class);
System.out.println(city);  // Smiljan

tesla.setPlaceOfBirth(null);
city = parser.parseExpression("PlaceOfBirth?.City").getValue(context, tesla, String.class);
System.out.println(city);  // null - does not throw NullPointerException!!!

16、集合選擇

// 語法.?[selectionExpression]
List<Inventor> list = (List<Inventor>) parser.parseExpression(
        "Members.?[Nationality == 'Serbian']").getValue(societyContext);

// 返回value小于27的值
Map newMap = parser.parseExpression("map.?[value<27]").getValue();

除了返回所有選定的元素之外,還可以只檢索第一個或最后一個值。要獲得匹配選擇的第一個條目,語法是。.^[selectionExpression].要獲得最后一個匹配的選擇,語法是。.$[選擇表達(dá)式]

17、集合投影

// 語法:.![projectionExpression]
// returns ['Smiljan', 'Idvor' ]
List placesOfBirth = (List)parser.parseExpression("Members.![placeOfBirth.city]");

18、表達(dá)式模板

// 通常使用#{}作為模板,與字符串拼接起來
String randomPhrase = parser.parseExpression(
        "random number is #{T(java.lang.Math).random()}",
        new TemplateParserContext()).getValue(String.class);

// evaluates to "random number is 0.7038186818312008"
// TemplateParserContext 的定義
public class TemplateParserContext implements ParserContext {

    public String getExpressionPrefix() {
        return "#{";
    }

    public String getExpressionSuffix() {
        return "}";
    }

    public boolean isTemplate() {
        return true;
    }
}

參考資料

https://docs.spring.io/spring-framework/docs/5.1.6.RELEASE/spring-framework-reference/core.html#expressions

到此這篇關(guān)于Spring中SpEL表達(dá)式的使用全解的文章就介紹到這了,更多相關(guān)Spring SpEL表達(dá)式內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Java入門之集合框架詳解

    Java入門之集合框架詳解

    本文介紹了Java集合框架體系結(jié)構(gòu),包括List、Set和Map接口及其常用實現(xiàn)類,重點講解了ArrayList、LinkedList、HashSet、TreeSet和HashMap等類的使用方法,并詳細(xì)介紹了泛型的定義和作用,最后,還討論了集合的遍歷和并發(fā)修改異常處理
    2025-01-01
  • 在SpringBoot中記錄用戶操作日志功能

    在SpringBoot中記錄用戶操作日志功能

    在Web應(yīng)用程序開發(fā)中,記錄用戶操作日志是一項非常重要的任務(wù),它可以幫助我們追蹤用戶行為,分析系統(tǒng)狀況,以及審計系統(tǒng)的安全性,本文將介紹如何在SpringBoot框架中實現(xiàn)用戶操作日志的記錄功能,感興趣的朋友一起看看吧
    2024-12-12
  • Spring?@DateTimeFormat日期格式化時注解場景分析

    Spring?@DateTimeFormat日期格式化時注解場景分析

    這篇文章主要介紹了Spring?@DateTimeFormat日期格式化時注解場景分析,本文通過實例代碼給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2023-05-05
  • Java實現(xiàn)圖片裁剪功能的示例詳解

    Java實現(xiàn)圖片裁剪功能的示例詳解

    這篇文章主要介紹了如何利用Java實現(xiàn)圖片裁剪功能,可以將圖片按照自定義尺寸進(jìn)行裁剪,文中的示例代碼講解詳細(xì),感興趣的可以了解一下
    2022-01-01
  • SpringBoot添加富文本編輯器操作步驟

    SpringBoot添加富文本編輯器操作步驟

    富文本編輯器是一種能夠編輯和展示富文本內(nèi)容的工具或程序,與純文本編輯器不同,富文本編輯器可以處理文本的格式、樣式、布局等方面,使文本更加豐富多樣,本文給大家介紹了SpringBoot添加富文本編輯器操作步驟,需要的朋友可以參考下
    2024-01-01
  • MyBatis-Plus如何使用枚舉自動關(guān)聯(lián)注入詳解

    MyBatis-Plus如何使用枚舉自動關(guān)聯(lián)注入詳解

    這篇文章主要給大家介紹了關(guān)于MyBatis-Plus如何使用枚舉自動關(guān)聯(lián)注入的相關(guān)資料,文中通過實例代碼介紹的非常詳細(xì),對大家學(xué)習(xí)或者使用MyBatis-Plus具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下
    2022-03-03
  • 解決springboot配置logback-spring.xml不起作用問題

    解決springboot配置logback-spring.xml不起作用問題

    這篇文章主要介紹了解決springboot配置logback-spring.xml不起作用問題,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-11-11
  • SSH框架網(wǎng)上商城項目第22戰(zhàn)之銀行圖標(biāo)以及支付頁面顯示

    SSH框架網(wǎng)上商城項目第22戰(zhàn)之銀行圖標(biāo)以及支付頁面顯示

    這篇文章主要為大家詳細(xì)介紹了SSH框架網(wǎng)上商城項目第22戰(zhàn)之銀行圖標(biāo)以及支付頁面顯示,感興趣的小伙伴們可以參考一下
    2016-06-06
  • Java Date與String的相互轉(zhuǎn)換詳解

    Java Date與String的相互轉(zhuǎn)換詳解

    這篇文章主要介紹了Java Date與String的相互轉(zhuǎn)換詳解的相關(guān)資料,需要的朋友可以參考下
    2017-02-02
  • 通過Spring AOP實現(xiàn)異常捕捉機制

    通過Spring AOP實現(xiàn)異常捕捉機制

    在開發(fā)過程中,異常處理是一個不可忽視的重要環(huán)節(jié),合理、優(yōu)雅地處理異常不僅能提高代碼的魯棒性,還能提升系統(tǒng)的用戶體驗,本文將介紹如何通過Spring AOP實現(xiàn)一個高效的異常捕捉機制,使得異常處理變得更加優(yōu)雅和統(tǒng)一,需要的朋友可以參考下
    2024-08-08

最新評論

鹤岗市| 安康市| 玛多县| 庆阳市| 会宁县| 轮台县| 凯里市| 翁牛特旗| 张家港市| 内江市| 望都县| 淄博市| 六盘水市| 全南县| 剑阁县| 阜平县| 栾川县| 旬邑县| 昌吉市| 博罗县| 吉木萨尔县| 黑山县| 开化县| 伊金霍洛旗| 伊川县| 治多县| 民县| 汉阴县| 都昌县| 佛冈县| 台东县| 汶上县| 五常市| 隆德县| 吴江市| 临西县| 镇雄县| 汕头市| 承德市| 略阳县| 汝州市|