欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Spring中字段格式化的使用小結(jié)

 更新時(shí)間:2022年06月26日 11:46:21   作者:Spring全家桶實(shí)戰(zhàn)案例  
Spring提供的一個(gè)core.convert包?是一個(gè)通用類型轉(zhuǎn)換系統(tǒng)。它提供了統(tǒng)一的?ConversionService??API和強(qiáng)類型的Converter SPI,用于實(shí)現(xiàn)從一種類型到另一種類型的轉(zhuǎn)換邏輯,這篇文章主要介紹了Spring中字段格式化的使用詳解,需要的朋友可以參考下

Spring提供的一個(gè)core.convert包 是一個(gè)通用類型轉(zhuǎn)換系統(tǒng)。它提供了統(tǒng)一的 ConversionService   API和強(qiáng)類型的Converter SPI,用于實(shí)現(xiàn)從一種類型到另一種類型的轉(zhuǎn)換邏輯。Spring容器使用這個(gè)系統(tǒng)綁定bean屬性值。此外,Spring Expression Language (SpEL)和DataBinder都使用這個(gè)系統(tǒng)來(lái)綁定字段值。例如,當(dāng)SpEL需要將Short強(qiáng)制轉(zhuǎn)換為L(zhǎng)ong來(lái)完成表達(dá)式時(shí)。setValue(對(duì)象bean,對(duì)象值)嘗試,核心。轉(zhuǎn)換系統(tǒng)執(zhí)行強(qiáng)制轉(zhuǎn)換。

現(xiàn)在考慮典型客戶端環(huán)境(例如web或桌面應(yīng)用程序)的類型轉(zhuǎn)換需求。在這種環(huán)境中,通常從String轉(zhuǎn)換為支持客戶端回發(fā)過(guò)程,并返回String以支持視圖呈現(xiàn)過(guò)程。此外,你經(jīng)常需要本地化String值。更一般的core.convert Converter SPI不能直接解決這些格式要求。為了直接解決這些問(wèn)題,Spring 3引入了一個(gè)方便的Formatter SPI,它為客戶端環(huán)境提供了PropertyEditor實(shí)現(xiàn)的一個(gè)簡(jiǎn)單而健壯的替代方案。

通常,當(dāng)你需要實(shí)現(xiàn)通用類型轉(zhuǎn)換邏輯時(shí),你可以使用Converter SPI,例如,用于java.util.Date和Long之間的轉(zhuǎn)換。當(dāng)你在客戶端環(huán)境(例如web應(yīng)用程序)中工作并需要解析和打印本地化的字段值時(shí),你可以使用Formatter SPI。ConversionService為這兩個(gè)spi提供了統(tǒng)一的類型轉(zhuǎn)換API。

1、Formatter SPI

實(shí)現(xiàn)字段格式化邏輯的Formatter SPI是簡(jiǎn)單且強(qiáng)類型的。下面的清單顯示了Formatter接口定義:

package org.springframework.format;
public interface Formatter<T> extends Printer<T>, Parser<T> {
}

Formatter繼承自Printer和Parser接口。

@FunctionalInterface
public interface Printer<T> {
  String print(T object, Locale locale);
}
@FunctionalInterface
public interface Parser<T> {
  T parse(String text, Locale locale) throws ParseException;
}

默認(rèn)情況下Spring容器提供了幾個(gè)Formatter實(shí)現(xiàn)。數(shù)字包提供了NumberStyleFormatter、CurrencyStyleFormatter和PercentStyleFormatter來(lái)格式化使用java.text.NumberFormat的number對(duì)象。datetime包提供了一個(gè)DateFormatter來(lái)用java.text.DateFormat格式化 java.util.Date對(duì)象。

自定義Formatter。

public class StringToNumberFormatter implements Formatter<Number> {
  @Override
  public String print(Number object, Locale locale) {
    return "結(jié)果是:" + object.toString();
  }
  @Override
  public Number parse(String text, Locale locale) throws ParseException {
    return NumberFormat.getInstance().parse(text);
  }
}

如何使用?我們可以通過(guò)FormattingConversionService 轉(zhuǎn)換服務(wù)進(jìn)行添加自定義的格式化類。

FormattingConversionService fcs = new FormattingConversionService();
// 默認(rèn)如果不添加自定義的格式化類,那么程序運(yùn)行將會(huì)報(bào)錯(cuò)
fcs.addFormatterForFieldType(Number.class, new StringToNumberFormatter());
Number number = fcs.convert("100.5", Number.class);
System.out.println(number);

查看源碼:

public class FormattingConversionService extends GenericConversionService implements FormatterRegistry, EmbeddedValueResolverAware {
  public void addFormatterForFieldType(Class<?> fieldType, Formatter<?> formatter) {
    addConverter(new PrinterConverter(fieldType, formatter, this));
    addConverter(new ParserConverter(fieldType, formatter, this));
  }
  private static class PrinterConverter implements GenericConverter {}
  private static class ParserConverter implements GenericConverter {}
}
public class GenericConversionService implements ConfigurableConversionService {
  private final Converters converters = new Converters();
  public void addConverter(GenericConverter converter) {
    this.converters.add(converter);
  }
}

Formatter最后還是被適配成GenericConverter(類型轉(zhuǎn)換接口)。

2、基于注解的格式化

字段格式化可以通過(guò)字段類型或注釋進(jìn)行配置。要將注釋綁定到Formatter,請(qǐng)實(shí)現(xiàn)AnnotationFormatterFactory。

public interface AnnotationFormatterFactory<A extends Annotation> {
  Set<Class<?>> getFieldTypes();
  Printer<?> getPrinter(A annotation, Class<?> fieldType);
  Parser<?> getParser(A annotation, Class<?> fieldType);
}

類及其方法說(shuō)明:

參數(shù)化A為字段注解類型,你希望將該字段與格式化邏輯關(guān)聯(lián),例如org.springframework.format.annotation.DateTimeFormat。

  • getFieldTypes()返回可以使用注釋的字段類型。
  • getPrinter()返回一個(gè)Printer來(lái)打印帶注釋的字段的值。
  • getParser()返回一個(gè)Parser來(lái)解析帶注釋字段的clientValue。

自定義注解解析器。

public class StringToDateFormatter implements AnnotationFormatterFactory<DateFormatter> {
  @Override
  public Set<Class<?>> getFieldTypes() {
    return new HashSet<Class<?>>(Arrays.asList(Date.class));
  }
  @Override
  public Printer<?> getPrinter(DateFormatter annotation, Class<?> fieldType) {
    return getFormatter(annotation, fieldType);
  }
  @Override
  public Parser<?> getParser(DateFormatter annotation, Class<?> fieldType) {
    return getFormatter(annotation, fieldType);
  }
  private StringFormatter getFormatter(DateFormatter annotation, Class<?> fieldType) {
    String pattern = annotation.value();
    return new StringFormatter(pattern);
  }
  class StringFormatter implements Formatter<Date> {
    private String pattern;
    public StringFormatter(String pattern) {
      this.pattern = pattern;
    }
    @Override
    public String print(Date date, Locale locale) {
      return DateTimeFormatter.ofPattern(pattern, locale).format(date.toInstant());
    }
    @Override
    public Date parse(String text, Locale locale) throws ParseException {
      DateTimeFormatter formatter = DateTimeFormatter.ofPattern(pattern, locale);
      return Date.from(LocalDate.parse(text, formatter).atStartOfDay().atZone(ZoneId.systemDefault()).toInstant());
    }
  }
}

注冊(cè)及使用:

public class Main {
  @DateFormatter("yyyy年MM月dd日")
  private Date date;
  public static void main(String[] args) throws Exception {
    FormattingConversionService fcs = new FormattingConversionService();
    fcs.addFormatterForFieldAnnotation(new StringToDateFormatter());
    Main main = new Main();
    Field field = main.getClass().getDeclaredField("date");
    TypeDescriptor targetType = new TypeDescriptor(field);
    Object result = fcs.convert("2022年01月21日", targetType);
    System.out.println(result);
    field.setAccessible(true);
    field.set(main, result);
    System.out.println(main.date);
  }
}

3、FormatterRegistry

FormatterRegistry是用于注冊(cè)格式化程序和轉(zhuǎn)換器的SPI。FormattingConversionService是FormatterRegistry的一個(gè)實(shí)現(xiàn),適用于大多數(shù)環(huán)境。可以通過(guò)編程或聲明的方式將該變體配置為Spring bean,例如使用FormattingConversionServiceFactoryBean。因?yàn)檫@個(gè)實(shí)現(xiàn)還實(shí)現(xiàn)了ConversionService,所以您可以直接配置它,以便與Spring的DataBinder和Spring表達(dá)式語(yǔ)言(SpEL)一起使用。

public interface FormatterRegistry extends ConverterRegistry {
  void addPrinter(Printer<?> printer);
  void addParser(Parser<?> parser);
  void addFormatter(Formatter<?> formatter);
  void addFormatterForFieldType(Class<?> fieldType, Formatter<?> formatter);
  void addFormatterForFieldType(Class<?> fieldType, Printer<?> printer, Parser<?> parser);
  void addFormatterForFieldAnnotation(AnnotationFormatterFactory<? extends Annotation> annotationFormatterFactory);
}

4、SpringMVC中配置類型轉(zhuǎn)換

@Configuration
@EnableWebMvc
public class WebConfig implements WebMvcConfigurer {
  @Override
  public void addFormatters(FormatterRegistry registry) {
    // ...
  }
}

SpringBoot中有如下的默認(rèn)類型轉(zhuǎn)換器。

public class WebMvcAutoConfiguration {
  public static class EnableWebMvcConfiguration extends DelegatingWebMvcConfiguration implements ResourceLoaderAware {
    @Bean
    @Override
    public FormattingConversionService mvcConversionService() {
      Format format = this.mvcProperties.getFormat();
      WebConversionService conversionService = new WebConversionService(new DateTimeFormatters().dateFormat(format.getDate()).timeFormat(format.getTime()).dateTimeFormat(format.getDateTime()));
      addFormatters(conversionService);
      return conversionService;
    }    
  }
}

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

相關(guān)文章

  • 詳解Sentinel流量控制限流框架的原理與使用

    詳解Sentinel流量控制限流框架的原理與使用

    Sentinel 是一個(gè)高可用、高擴(kuò)展、高穩(wěn)定性的開(kāi)源流量控制和熔斷降級(jí)框架,可以在分布式系統(tǒng)中實(shí)現(xiàn)實(shí)時(shí)的流量控制,下面就來(lái)和大家聊聊是具體如何操作的吧
    2023-05-05
  • java 漢諾塔Hanoi遞歸、非遞歸(仿系統(tǒng)遞歸)和非遞歸規(guī)律 實(shí)現(xiàn)代碼

    java 漢諾塔Hanoi遞歸、非遞歸(仿系統(tǒng)遞歸)和非遞歸規(guī)律 實(shí)現(xiàn)代碼

    漢諾塔(Hanoi) 算法Java實(shí)現(xiàn)。通過(guò)三個(gè)函數(shù),分別對(duì)Hanoi進(jìn)行遞歸、非遞歸和非遞歸規(guī)律實(shí)現(xiàn)。
    2013-05-05
  • Java中常用的設(shè)計(jì)模式之模板模式詳解

    Java中常用的設(shè)計(jì)模式之模板模式詳解

    這篇文章主要為大家詳細(xì)介紹了Python實(shí)現(xiàn)學(xué)生成績(jī)管理系統(tǒng),使用數(shù)據(jù)庫(kù),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2022-02-02
  • Spring data jpa的使用與詳解(復(fù)雜動(dòng)態(tài)查詢及分頁(yè),排序)

    Spring data jpa的使用與詳解(復(fù)雜動(dòng)態(tài)查詢及分頁(yè),排序)

    這篇文章主要介紹了Spring data jpa的使用與詳解(復(fù)雜動(dòng)態(tài)查詢及分頁(yè),排序),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2020-11-11
  • 使用java代碼獲取新浪微博應(yīng)用的access token代碼實(shí)例

    使用java代碼獲取新浪微博應(yīng)用的access token代碼實(shí)例

    這篇文章主要介紹了使用java代碼獲取新浪微博應(yīng)用的access token實(shí)例,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2019-05-05
  • Java中為何要使用ArrayList

    Java中為何要使用ArrayList

    這篇文章主要介紹了Java中為何要使用ArrayList,幫助大家更好的理解和學(xué)習(xí)Java,感興趣的朋友可以了解下
    2020-09-09
  • Maven實(shí)戰(zhàn)之搭建Maven私服和鏡像的方法(圖文)

    Maven實(shí)戰(zhàn)之搭建Maven私服和鏡像的方法(圖文)

    本篇文章主要介紹了搭建Maven私服和鏡像的方法(圖文),小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2017-12-12
  • Spring?Boot集成RabbitMQ以及隊(duì)列模式操作

    Spring?Boot集成RabbitMQ以及隊(duì)列模式操作

    RabbitMQ是實(shí)現(xiàn)AMQP(高級(jí)消息隊(duì)列協(xié)議)的消息中間件的一種,下面這篇文章主要給大家介紹了關(guān)于Spring?Boot集成RabbitMQ以及隊(duì)列模式操作的相關(guān)資料,文中通過(guò)實(shí)例代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2022-04-04
  • JRebel在線激活破解實(shí)現(xiàn)教程

    JRebel在線激活破解實(shí)現(xiàn)教程

    這篇文章主要介紹了JRebel在線激活破解實(shí)現(xiàn)教程,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-12-12
  • Eolink上傳文件到Java后臺(tái)進(jìn)行處理的示例代碼

    Eolink上傳文件到Java后臺(tái)進(jìn)行處理的示例代碼

    這篇文章主要介紹了Eolink上傳文件到Java后臺(tái)進(jìn)行處理,這里是上傳的excel表格數(shù)據(jù)并轉(zhuǎn)換為java集合對(duì)象、然后進(jìn)行業(yè)務(wù)邏輯處理判斷最后保存到數(shù)據(jù)庫(kù)?,需要的朋友可以參考下
    2022-12-12

最新評(píng)論