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

Java的@Repeatable注解使用詳細(xì)解析

 更新時(shí)間:2024年02月02日 08:32:51   作者:小徐也要努力鴨  
這篇文章主要介紹了Java的@Repeatable注解使用詳細(xì)解析,java8新增了注解@Repeatable,在hibernate-validator的源碼注解如@MAX、@NotNull等中,有@Repeatable注解的使用,需要的朋友可以參考下

1 前言

java8新增了注解@Repeatable,在hibernate-validator的源碼注解如@MAX、@NotNull等中,有@Repeatable注解的使用,源碼示例如下:

/*
 * Jakarta Bean Validation API
 *
 * License: Apache License, Version 2.0
 * See the license.txt file in the root directory or <http://www.apache.org/licenses/LICENSE-2.0>.
 */
package javax.validation.constraints;
import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
import static java.lang.annotation.ElementType.CONSTRUCTOR;
import static java.lang.annotation.ElementType.FIELD;
import static java.lang.annotation.ElementType.METHOD;
import static java.lang.annotation.ElementType.PARAMETER;
import static java.lang.annotation.ElementType.TYPE_USE;
import static java.lang.annotation.RetentionPolicy.RUNTIME;
import java.lang.annotation.Documented;
import java.lang.annotation.Repeatable;
import java.lang.annotation.Retention;
import java.lang.annotation.Target;
import javax.validation.Constraint;
import javax.validation.Payload;
import javax.validation.constraints.NotNull.List;
/**
 * The annotated element must not be {@code null}.
 * Accepts any type.
 *
 * @author Emmanuel Bernard
 */
@Target({ METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER, TYPE_USE })
@Retention(RUNTIME)
@Repeatable(List.class)
@Documented
@Constraint(validatedBy = { })
public @interface NotNull {
	String message() default "{javax.validation.constraints.NotNull.message}";
	Class<?>[] groups() default { };
	Class<? extends Payload>[] payload() default { };
	/**
	 * Defines several {@link NotNull} annotations on the same element.
	 *
	 * @see javax.validation.constraints.NotNull
	 */
	@Target({ METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER, TYPE_USE })
	@Retention(RUNTIME)
	@Documented
	@interface List {
		NotNull[] value();
	}
}

2 使用

參考hibernate-validator注解,使用@Repeatable:

2.1 新建注解RepeaDemo

暫時(shí)不添加@Repeatable:

package com.xiaoxu.tool.demo;

import java.lang.annotation.*;

@Target(value = {ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface RepeaDemo {
    String id();
    String name();
}

新建demo類:

package com.xiaoxu.tool.demo;
import java.lang.reflect.Field;
import java.util.Arrays;
/**
 * @author xiaoxu
 * @date 2022-05-17
 * spring_boot:com.xiaoxu.tool.demo.TestRepeatable
 */
public class TestRepeatable {
    @RepeaDemo(id = "1001",name = "荔枝")
    private String fruit1;
    @RepeaDemo(id = "1002",name = "葡萄")
    private String fruit2;
    public static void demo1(){
        Class<?> a = TestRepeatable.class;
        Field[] fruits = a.getDeclaredFields();
        Arrays.stream(fruits).forEach(f->{
            if(f.isAnnotationPresent(RepeaDemo.class)){
                RepeaDemo anno = f.getAnnotation(RepeaDemo.class);
                String id = anno.id();
                String name = anno.name();
                System.out.printf("水果id:%s,水果名稱:%s%n",id,name);
            }
        });
    }
    public static void main(String[] args) {
        demo1();
    }
}

執(zhí)行結(jié)果如下:

水果id:1001,水果名稱:荔枝
水果id:1002,水果名稱:葡萄

但是問題是,如果希望在字段上增加多個(gè)注解,那么會(huì)提示Duplicate annotation.錯(cuò)誤:

在這里插入圖片描述

于是考慮新增一個(gè)RepeaDemos注解,用于存儲(chǔ)@RepeaDemo注解數(shù)組,就可以達(dá)到多個(gè)注解的使用了,如下:

package com.xiaoxu.tool.demo;

import java.lang.annotation.*;

@Target(value = {ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface RepeaDemos {
    RepeaDemo[] repeaDemos();
}

修改TestRepeatable代碼:

package com.xiaoxu.tool.demo;

import java.lang.reflect.Field;
import java.util.Arrays;

/**
 * @author xiaoxu
 * @date 2022-05-17
 * spring_boot:com.xiaoxu.tool.demo.TestRepeatable
 */
public class TestRepeatable {
    @RepeaDemos(repeaDemos = {
        @RepeaDemo(id = "1001",name = "荔枝"),
        @RepeaDemo(id = "1003",name = "沃柑")
    })
    private String fruit1;

    @RepeaDemo(id = "1002",name = "葡萄")
    private String fruit2;

    public static void demo1(){
        Class<?> a = TestRepeatable.class;
        Field[] fruits = a.getDeclaredFields();
        Arrays.stream(fruits).forEach(f->{
            if(f.isAnnotationPresent(RepeaDemo.class)){
                RepeaDemo anno = f.getAnnotation(RepeaDemo.class);
                String id = anno.id();
                String name = anno.name();
                System.out.printf("水果id:%s,水果名稱:%s%n",id,name);
            }
        });
    }

    public static void demo2(){
        Class<?> a = TestRepeatable.class;
        Field[] fruits = a.getDeclaredFields();
        Arrays.stream(fruits).forEach(f->{
            if(f.isAnnotationPresent(RepeaDemos.class)){
                RepeaDemos anno = f.getAnnotation(RepeaDemos.class);
                RepeaDemo[] res= anno.repeaDemos();
                Arrays.stream(res).forEach(r-> System.out.printf("水果id:%s,水果名稱:%s%n",r.id(),r.name()));
            }
            if(f.isAnnotationPresent(RepeaDemo.class)){
                RepeaDemo anno = f.getAnnotation(RepeaDemo.class);
                String id = anno.id();
                String name = anno.name();
                System.out.printf("水果id:%s,水果名稱:%s%n",id,name);
            }
        });
    }
    public static void main(String[] args) {
        demo2();
    }
}

執(zhí)行結(jié)果如下:

水果id:1001,水果名稱:荔枝
水果id:1003,水果名稱:沃柑
水果id:1002,水果名稱:葡萄

2.2 @Repeatable注解使用

對(duì)于上述注解使用,@Repeatable注解的作用就是使得@RepeaDemo注解可以多個(gè)添加在字段上,而最外層無(wú)須包裹@RepeaDemos注解,當(dāng)然,@RepeaDemos注解任然需要保留,修改如下:

修改@RepeaDemos注解(注意@RepeaDemos注解,必須改為value()才可以):

package com.xiaoxu.tool.demo;

import java.lang.annotation.*;

@Target(value = {ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface RepeaDemos {
    RepeaDemo[] value();
}

修改@RepeaDemo注解,增加@Repeatable,參數(shù)為RepeaDemos.class:

package com.xiaoxu.tool.demo;

import java.lang.annotation.*;

@Target(value = {ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Repeatable(RepeaDemos.class)
@Documented
public @interface RepeaDemo {
    String id();
    String name();
}

修改demo類:

package com.xiaoxu.tool.demo;
import java.lang.reflect.Field;
import java.util.Arrays;
/**
 * @author xiaoxu
 * @date 2022-05-17
 * spring_boot:com.xiaoxu.tool.demo.TestRepeatable
 */
public class TestRepeatable {
//    @RepeaDemos(value = {
//        @RepeaDemo(id = "1001",name = "荔枝"),
//        @RepeaDemo(id = "1003",name = "沃柑")
//    })
    @RepeaDemo(id = "1001",name = "荔枝")
    @RepeaDemo(id = "1003",name = "沃柑")
    private String fruit1;
    @RepeaDemo(id = "1002",name = "葡萄")
    private String fruit2;
    public static void demo1(){
        Class<?> a = TestRepeatable.class;
        Field[] fruits = a.getDeclaredFields();
        Arrays.stream(fruits).forEach(f->{
            if(f.isAnnotationPresent(RepeaDemo.class)){
                RepeaDemo anno = f.getAnnotation(RepeaDemo.class);
                String id = anno.id();
                String name = anno.name();
                System.out.printf("水果id:%s,水果名稱:%s%n",id,name);
            }
        });
    }
    public static void demo2(){
        Class<?> a = TestRepeatable.class;
        Field[] fruits = a.getDeclaredFields();
        Arrays.stream(fruits).forEach(f->{
            if(f.isAnnotationPresent(RepeaDemos.class)){
                RepeaDemos anno = f.getAnnotation(RepeaDemos.class);
                RepeaDemo[] res= anno.value();
                Arrays.stream(res).forEach(r-> System.out.printf("水果id:%s,水果名稱:%s%n",r.id(),r.name()));
            }
            if(f.isAnnotationPresent(RepeaDemo.class)){
                RepeaDemo anno = f.getAnnotation(RepeaDemo.class);
                String id = anno.id();
                String name = anno.name();
                System.out.printf("水果id:%s,水果名稱:%s%n",id,name);
            }
        });
    }
    public static void main(String[] args) {
        demo2();
    }
}

執(zhí)行效果如下:

水果id:1001,水果名稱:荔枝
水果id:1003,水果名稱:沃柑
水果id:1002,水果名稱:葡萄

可見,如下兩種方式,獲取的結(jié)果是一致的,其實(shí)@Repeatable注解就是一種語(yǔ)法糖(類似于python的裝飾器語(yǔ)法糖等等),本質(zhì)上在java編譯時(shí),使用如下的第2種注解方式,等同于使用第1種:

//1:
@RepeaDemos(value = {
    @RepeaDemo(id = "1001",name = "荔枝"),
    @RepeaDemo(id = "1003",name = "沃柑")
})
//2:
@RepeaDemo(id = "1001",name = "荔枝")
@RepeaDemo(id = "1003",name = "沃柑")

2.3 小結(jié)

1 @Repeatable注解使用前,需先增加一個(gè)注解的屬性值為子注解數(shù)組,且名稱為value()的父注解;

2 @Repeatable注解需要在子注解上標(biāo)注,且@Repeatable注解的值為父注解class;

3 @Repeatable注解本質(zhì)上是一種語(yǔ)法糖。

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

相關(guān)文章

  • spring cloud gateway使用 uri: lb://方式配置時(shí),服務(wù)名的特殊要求

    spring cloud gateway使用 uri: lb://方式配置時(shí),服務(wù)名的特殊要求

    這篇文章主要介紹了spring cloud gateway使用 uri: lb://方式配置時(shí),服務(wù)名的特殊要求,本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2020-12-12
  • 將字符串?dāng)?shù)字格式化為樣式1,000,000,000的方法

    將字符串?dāng)?shù)字格式化為樣式1,000,000,000的方法

    這篇文章主要介紹了將字符串?dāng)?shù)字格式化為樣式1,000,000,000的方法,有需要的朋友可以參考一下
    2014-01-01
  • Java實(shí)現(xiàn)壓縮 PDF文件大小的示例代碼

    Java實(shí)現(xiàn)壓縮 PDF文件大小的示例代碼

    在日常工作中,我們經(jīng)常會(huì)遇到 PDF 文件體積過大的問題,本文將為你揭示如何利用 Spire.PDF for Java 輕松實(shí)現(xiàn) PDF 文件大小的優(yōu)化與壓縮,感興趣的可以了解下
    2025-09-09
  • Java中線程Thread的特點(diǎn)及使用

    Java中線程Thread的特點(diǎn)及使用

    這篇文章主要介紹了Java中線程的特點(diǎn)及使用,線程是進(jìn)程的組成部分,一個(gè)進(jìn)程可以擁有多個(gè)線程,而一個(gè)線程必須擁有一個(gè)父進(jìn)程,那么線程該如何使用,讓我們一起來(lái)看看吧
    2023-04-04
  • springboot實(shí)現(xiàn)攔截器的3種方式及異步執(zhí)行的思考

    springboot實(shí)現(xiàn)攔截器的3種方式及異步執(zhí)行的思考

    實(shí)際項(xiàng)目中,我們經(jīng)常需要輸出請(qǐng)求參數(shù),響應(yīng)結(jié)果,方法耗時(shí),統(tǒng)一的權(quán)限校驗(yàn)等。本文首先為大家介紹 HTTP 請(qǐng)求中三種常見的攔截實(shí)現(xiàn),并且比較一下其中的差異。感興趣的可以了解一下
    2021-07-07
  • springboot整合mqtt客戶端示例分享

    springboot整合mqtt客戶端示例分享

    這篇文章主要介紹了springboot整合mqtt客戶端示例分享的相關(guān)資料,需要的朋友可以參考下
    2023-07-07
  • java實(shí)現(xiàn)文件上傳的詳細(xì)步驟

    java實(shí)現(xiàn)文件上傳的詳細(xì)步驟

    文件上傳是用戶將本地文件通過Web頁(yè)面提交到服務(wù)器的過程,涉及客戶端、服務(wù)器端、上傳表單等組件,在SpringBoot中,通過MultipartFile接口處理上傳文件,并將其保存在服務(wù)器,文中通過代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2024-10-10
  • Java設(shè)計(jì)模式之觀察者模式詳解

    Java設(shè)計(jì)模式之觀察者模式詳解

    這篇文章主要介紹了Java設(shè)計(jì)模式之觀察者模式詳解,對(duì)象之間的多對(duì)一依賴的一種設(shè)計(jì)方案,被依賴的對(duì)象為Subject,依賴的對(duì)象為Observer,Subject通知Observer變化,需要的朋友可以參考下
    2023-12-12
  • 深入Java萬(wàn)物之母Object類詳情

    深入Java萬(wàn)物之母Object類詳情

    這篇文章主要介紹了Java萬(wàn)物之母Object類詳情,Object類,它是所有類的默認(rèn)父類 ,子類不用使用extends關(guān)鍵字繼承它,不管是JDK中的類,還是自定義的類
    2022-06-06
  • Java下SpringBoot創(chuàng)建定時(shí)任務(wù)詳解

    Java下SpringBoot創(chuàng)建定時(shí)任務(wù)詳解

    這篇文章主要介紹了Java下SpringBoot創(chuàng)建定時(shí)任務(wù)詳解,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2020-07-07

最新評(píng)論

镇江市| 康乐县| 皮山县| 龙井市| 翼城县| 郁南县| 云阳县| 马尔康县| 灵武市| 池州市| 那坡县| 松桃| 龙川县| 湘潭市| 前郭尔| 延川县| 福安市| 子洲县| 瑞金市| 巨鹿县| 亳州市| 太康县| 屏南县| 绥滨县| 青龙| 北碚区| 马公市| 灵石县| 赤水市| 兴安县| 庆阳市| 云霄县| 建始县| 庆阳市| 苏尼特右旗| 前郭尔| 长沙县| 津市市| 浏阳市| 张家界市| 卢湾区|