Rozważ następujący kod:
A.java:
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
@Retention(RetentionPolicy.RUNTIME)
@interface A{}
C.java:
import java.util.*;
@A public class C {
public static void main(String[] args){
System.out.println(Arrays.toString(C.class.getAnnotations()));
}
}
Kompilowanie i uruchamianie działa zgodnie z oczekiwaniami:
$ javac *.java
$ java -cp . C
[@A()]
Ale rozważ to:
$ rm A.class
$ java -cp . C
[]
Spodziewałbym się, że wyrzuci ClassNotFoundException
, ponieważ @A
brakuje. Ale zamiast tego po cichu odrzuca adnotację.
Czy to zachowanie zostało gdzieś udokumentowane w JLS, czy jest to dziwactwo JVM firmy Sun? Jakie jest tego uzasadnienie?
Wydaje się to wygodne w przypadku takich rzeczy javax.annotation.Nonnull
(co wydaje się, że i tak powinno być @Retention(CLASS)
), ale w przypadku wielu innych adnotacji wydaje się, że może powodować różne złe rzeczy w czasie wykonywania.
źródło