Java 菜鳥教程

Java 流程控制

Java 數(shù)組

Java 面向?qū)ο?I)

Java 面向?qū)ο?II)

Java 面向?qū)ο?III)

Java 異常處理

Java 列表(List)

Java Queue(隊列)

Java Map集合

Java Set集合

Java 輸入輸出(I/O)

Java Reader/Writer

Java 其他主題

Java 注解類型

在本教程中,我們將借助示例學(xué)習(xí)不同類型的Java注解。

Java注解是我們程序源代碼的元數(shù)據(jù)(有關(guān)數(shù)據(jù)的數(shù)據(jù))。Java SE提供了幾個預(yù)定義的注解。此外,我們還可以根據(jù)需要創(chuàng)建自定義注解。

如果您不知道什么是注解,請訪問Java注解教程。

這些注解可以分類為:

1. 預(yù)定義的注解

  • @Deprecated

  • @Override

  • @SuppressWarnings

  • @SafeVarargs

  • @FunctionalInterface

2. 自定義注解

3. 元注解

  • @Retention

  • @Documented

  • @Target

  • @Inherited

  • @Repeatable

預(yù)定義的注解類型

1. @Deprecated

@Deprecated注解是一個標(biāo)記注解指示元素(類,方法,字段等)已過時,并已被更新的元素取代。

其語法為:

@Deprecated
accessModifier returnType deprecatedMethodName() { ... }

當(dāng)程序使用已聲明為已棄用的元素時,編譯器將生成警告。

我們使用Javadoc @deprecated標(biāo)記來記錄已棄用的元素。

/**
 * @deprecated
 * 為什么它被棄用
 */
@Deprecated
accessModifier returnType deprecatedMethodName() { ... }

示例1:@Deprecated 注解示例

class Main {
  /**
   * @deprecated
   * 此方法已棄用,并已由newMethod()代替
   */
  @Deprecated
  public static void deprecatedMethod() { 
    System.out.println("Deprecated method"); 
  } 

  public static void main(String args[]) {
    deprecatedMethod();
  }
}

輸出結(jié)果

Deprecated method

2. @Override

@Override 注解指定子類的方法用相同的方法名、返回類型和參數(shù)列表覆蓋父類的方法。

@Override在重寫方法時,并非必須使用。 但是,如果使用它,則在覆蓋方法時,如果出現(xiàn)錯誤(例如錯誤的參數(shù)類型),則編譯器將給出錯誤。

示例2:@Override注解示例

class Animal {

  //重寫方法
  public void display(){
    System.out.println("I am an animal");
  }
}

class Dog extends Animal {

  //重寫方法
  @Override
  public void display(){
    System.out.println("I am a dog");
  }

  public void printMessage(){
    display();
  }
}

class Main {
  public static void main(String[] args) {
    Dog dog1 = new Dog();
    dog1.printMessage();
  }
}

輸出結(jié)果

I am a dog

在本示例中,通過創(chuàng)建Dog類的對象dog1,我們可以調(diào)用它的方法printMessage(),然后該方法執(zhí)行display()語句。

由于display()在兩個類中均已定義,因此Dog子類的display()方法將覆蓋超類Animal的display()方法。因此,子類的display()被調(diào)用。

3. @SuppressWarnings

顧名思義,@SuppressWarnings注解指示編譯器禁止執(zhí)行程序時生成的警告。

我們可以指定要取消的警告類型??梢越沟木媸翘囟ㄓ诰幾g器的,但警告分為兩類:棄用未檢查。

為了禁止顯示特定類別的警告,我們刻意使用:

@SuppressWarnings("warningCategory")

例如,

@SuppressWarnings("deprecated")

為了禁止顯示多個類別警告,我們刻意使用:

@SuppressWarnings({"warningCategory1", "warningCategory2"})

例如,

@SuppressWarnings({"deprecated", "unchecked"})

當(dāng)我們使用不推薦使用的元素時,deprecated類別指示編譯器禁止顯示警告。

當(dāng)我們使用原始類型時,unchecked類別指示編譯器禁止顯示警告。

并且,未定義的警告將被忽略。例如,

@SuppressWarnings("someundefinedwarning")

示例3:@SuppressWarnings 注解示例

class Main {
  @Deprecated
  public static void deprecatedMethod() { 
    System.out.println("Deprecated method"); 
  } 
  
  @SuppressWarnings("deprecated")
  public static void main(String args[]) {
    Main depObj = new Main();
    depObj. deprecatedMethod();
  }
}

輸出結(jié)果

Deprecated method

在這里,deprecatedMethod()已被標(biāo)記為已棄用,使用時會發(fā)出編譯器警告。通過使用@SuppressWarnings("deprecated")注解,我們可以避免編譯器警告。

4. @SafeVarargs

@SafeVarargs注解斷言,帶注解的方法或構(gòu)造不執(zhí)行它的可變參數(shù)不安全的操作(可變的參數(shù)數(shù))。

我們只能在不能被重寫的方法或構(gòu)造函數(shù)上使用此注解。這是因為重寫它們的方法可能會執(zhí)行不安全的操作。

在Java 9之前,我們只能在final或static方法上使用此注解,因為它們不能被重寫?,F(xiàn)在,我們也可以將此注解用于私有方法。

示例4:@SafeVarargs注解示例

import java.util.*;

class Main {

  private void displayList(List<String>... lists) {
    for (List<String> list : lists) {
      System.out.println(list);
    }
  }

  public static void main(String args[]) {
    Main obj = new Main();

    List<String> universityList = Arrays.asList("Tribhuvan University", "Kathmandu University");
    obj.displayList(universityList);

    List<String> programmingLanguages = Arrays.asList("Java", "C");
    obj.displayList(universityList, programmingLanguages);
  }
}

警告事項

Type safety: Potential heap pollution via varargs parameter lists
Type safety: A generic array of List<String> is created for a varargs 
 parameter

輸出結(jié)果

Note: Main.java uses unchecked or unsafe operations.
[Tribhuvan University, Kathmandu University]
[Tribhuvan University, Kathmandu University]
[Java, C]

在此,List ... list指定類型為List的變長參數(shù)。 這意味著方法displayList()可以具有零個或多個參數(shù)。

上面的程序編譯沒有錯誤,但是在不使用@SafeVarargs 注解時會發(fā)出警告。

在上面的示例中使用@SafeVarargs注解時,

@SafeVarargs
 private void displayList(List<String>... lists) { ... }

我們得到相同的輸出,但沒有任何警告。當(dāng)使用此注解時,未經(jīng)檢查的警告也會被刪除。

5. @FunctionalInterface

Java 8首先引入了此@FunctionalInterface注解。此注解表明使用它的類型聲明是一個功能接口。一個功能接口只能有一個抽象方法。

示例5:@FunctionalInterface注解示例

@FunctionalInterface
public interface MyFuncInterface{
  public void firstMethod(); //這是一個抽象的方法
}

如果我們添加另一個抽象方法,那么

@FunctionalInterface
public interface MyFuncInterface{
  public void firstMethod(); // 這是一個抽象的方法
  public void secondMethod(); //這會引發(fā)編譯錯誤
}

現(xiàn)在,當(dāng)我們運(yùn)行程序時,我們將收到以下警告:

Unexpected @FunctionalInterface annotation
@FunctionalInterface ^ MyFuncInterface is not a functional interface
multiple non-overriding abstract methods found in interface MyFuncInterface

使用@FunctionalInterface注解不是強(qiáng)制性的。編譯器會將滿足功能接口定義的任何接口視為功能接口。

我們使用此注解的目的,是確保功能接口只有一種抽象方法。

但是,它可以有任意數(shù)量的默認(rèn)方法和靜態(tài)方法,因為它們都有實現(xiàn)。

@FunctionalInterface
public interface MyFuncInterface{
  public void firstMethod(); //這是一種抽象方法
  default void secondMethod() { ... } 
  default void thirdMethod() { ... } 
}

自定義注解

也可以創(chuàng)建我們自己的自定義注解。

其語法為:

[Access Specifier] @interface<AnnotationName> {         
  DataType <Method Name>() [default value];
}

這是您需要了解的有關(guān)自定義注解的信息:

  • 注解可以通過使用@interface后面跟注解名稱來創(chuàng)建。

  • 注解可以具有看起來像方法的元素,但是它們沒有實現(xiàn)。

  • 默認(rèn)值是可選的。參數(shù)不能為空值。

  • 方法的返回類型可以是原始,枚舉,字符串,類名或這些類型的數(shù)組。

示例6:自定義注解示例

@interface MyCustomAnnotation {
  String value() default "default value";
}

class Main {
  @MyCustomAnnotation(value = "nhooo")
  public void method1() {
    System.out.println("測試方法1");
  }

  public static void main(String[] args) throws Exception {
    Main obj = new Main();
    obj.method1();
  }
}

輸出結(jié)果

測試方法1

元注解

元注解是應(yīng)用于其他注解的注解。

1. @Retention

@Retention注解指定了該注解可用的最高級別。

其語法為:

@Retention(RetentionPolicy)

有三種類型:

  • RetentionPolicy.SOURCE - 注解僅在源級別可用,并且被編譯器忽略。

  • RetentionPolicy.CLASS - 注解在編譯時可供編譯器使用,但Java虛擬機(jī)(JVM)會忽略它。

  • RetentionPolicy.RUNTIME - 注解可用于JVM。

例如,

@Retention(RetentionPolicy.RUNTIME)
public @interface MyCustomAnnotation{ ... }

2. @Documented

默認(rèn)情況下,自定義注解不包含在官方Java文檔中。要將注解包含在Javadoc文檔中,請使用@Documented注解。

例如,

@Documented
public @interface MyCustomAnnotation{ ... }

3. @Target

我們可以使用@Target注解將注解限制為應(yīng)用于特定目標(biāo)。

其語法為:

@Target(ElementType)

ElementType可有以下幾種類型之一:

元素類型Target
ElementType.ANNOTATION_TYPE注解類型
ElementType.CONSTRUCTOR構(gòu)造函數(shù)
ElementType.FIELD字段
ElementType.LOCAL_VARIABLE局部變量
ElementType.METHOD方法
ElementType.PACKAGE
ElementType.PARAMETER參數(shù)
ElementType.TYPE用于描述類、接口(包括注解類型) 或enum聲明

例如,

@Target(ElementType.METHOD)
public @interface MyCustomAnnotation{ ... }

在此示例中,我們僅將此注解的使用限制為方法。

注意:如果未定義目標(biāo)類型,則注解可用于任何元素。

4. @Inherited

默認(rèn)情況下,注解類型不能從超類繼承。但是,如果需要將注解從超類繼承到子類,則可以使用@Inherited注解。

其語法為:

@Inherited

例如,

@Inherited
public @interface MyCustomAnnotation { ... }

@MyCustomAnnotation
public class ParentClass{ ... }

public class ChildClass extends ParentClass { ... }

5. @Repeatable

帶有@Repeatable標(biāo)記的注解可以多次應(yīng)用于同一聲明。

@Repeatable(Universities.class)
public @interface University {
  String name();
}

@Repeatable注解中定義的值是容器注解。容器注解具有上述可重復(fù)注解數(shù)組類型的變量值(value)。在這里,Universities是包含注解類型的。

public @interface Universities {
  University[] value();
}

現(xiàn)在,@University注解可以在同一聲明上多次使用。

@University(name = "TU")
@University(name = "KU")
private String uniName;

如果需要檢索注解數(shù)據(jù),可以使用反射。

要檢索注解值,我們使用反射API中定義的getAnnotationsByType()或getAnnotations()方法。

丰满人妻一级特黄a大片,午夜无码免费福利一级,欧美亚洲精品在线,国产婷婷成人久久Av免费高清