Many frameworks now use annotations, and a typical spring can see a lot of annotations, such as @service, @Controller this type of annotation. Annotation Annotation is a very important feature of Java. Here's a look at some of the details about the annotations.
1. First, what is an annotation?
The more official explanation is that annotations are metadata, which is the data that explains the data. To be more popular, it is a kind of metadata that can modify the data such as classes, variables, methods, parameters, and so on. In a simple example, one of the annotations we often see is @ Override
. such as the following code.
Package Com.xdx.learn; Public class Father { publicvoid func () { System.out.println ("Hello");} } class extends father{ @Override publicvoid func () { System.out.println ( "HI");} }
You can see that the Func () method of the parent class is overridden in the son class, and we use a @override annotation to modify the method. Its role is to tell the compiler, this method overrides the method of the parent class, if I accidentally write Func as Func, the compiler because I have learned that I want to overwrite the parent class Func method, will prompt me, the parent class does not have a method called Func, I will go to check, oh, originally I wrote wrong AH.
So annotations play a role in modifying metadata, and the modified metadata has certain features that are exploited during program compilation, runtime, and so on. We don't have to take care of how it works. The provider who provided the note will take care of it.
For example, in spring, a member variable annotated with @resource is injected into an instance of the class when the class is instantiated. And how to use the @resource annotation to achieve this process, spring helped us do.
2. Definition of annotations
Let's take a look at the above-mentioned @Resource
How the inside of the annotation is defined.
@Target ({TYPE, FIELD, METHOD}) @Retention (RUNTIME) Public@InterfaceResource {String name ()default""; String lookup ()default""; Class<?> type ()defaultJava.lang.Object.class; enumAuthenticationType {CONTAINER, application} authenticationtype AuthenticationType () defaultAuthenticationtype.container; BooleanShareable ()default true; String Mappedname ()default""; String description ()default"";}
The above is the definition of an annotation, you can see that this annotation is modified by two meta-annotations, respectively, @target and @retention
Let's take a look at @target.
@Documented @retention (retentionpolicy.runtime) @Target (elementtype.annotation_type) public @Interface Target { /** * Returns An array of the kinds of element s an annotation type * can is applied to. @return An array of the kinds of elements a annotation type * can be applied to*/ Ele Menttype[] Value ();}
It is also decorated with three meta-annotations, with the exception of @target and @retention, and a @Documented.
In fact, there are a total of 4 meta-annotations, @Target, @Retention,@Documented,@Inherited.
@Target-Indicates the scope of the program element to which the annotation of that type can be annotated (the action target). The value of this meta-annotation can be type,method,constructor,field and so on. if the Target element annotations do not appear, then the defined annotations can be applied to any element of the program . By the definition of the note above @interface Target , we can see that its value is an array of enumerated types. In fact, their specific values are as follows.
Public enumElementType {/**Class, interface (including annotation type), or enum declaration*/TYPE,/**Field declaration (includes enum constants)*/FIELD,/**Method Declaration*/METHOD,/**formal parameter declaration*/PARAMETER,/**Constructor Declaration*/CONSTRUCTOR,/**Local Variable Declaration*/local_variable,/**Annotation Type declaration*/Annotation_type,/**Package Declaration*/Package ,/*** Type Parameter declaration * *@since1.8*/Type_parameter,/*** Use of a type * *@since1.8*/Type_use}
@Documented-the annotation of classes and methods are not present in Javadoc by default. If the annotation is decorated with @documented, it can appear in Javadoc.
when defining annotation, the @Documented is optional, and if not defined, annotation does not appear in Javadoc.
@Retention---Specify the lifetime of the annotation, that is, when it can survive, let's look at the specific definition of @Retention .
@Documented @retention (retentionpolicy.runtime) @Target (elementtype.annotation_type) public @Interface Retention { /** * Returns the Retention policy. @return the retention policy * /Retentionpolicy value ();}
Then let's look at retentionpolicy which objects this enumeration class has.
Public enumRetentionpolicy {/*** Annotations is to being discarded by the compiler. */SOURCE,/*** Annotations is to being recorded in the class file by the compiler * and need not being retained by the VM at RU N Time. This is the default * behavior. */CLASS,/*** Annotations is to being recorded in the class file by the compiler and * retained by the VM at run time, so T Hey may be read reflectively. * * @seejava.lang.reflect.AnnotatedElement*/RUNTIME}
It is clear that there are 3 life cycles of annotations that can survive, the compile phase, the stored in the. class file, and the running phase. It is important to note that only when the annotated Retention is retentionpolicy.runtime , can we get the annotation information of the method or class through reflection. Because the reflection mechanism works in the run phase after the class loading is complete.
@Inherited-If a class's annotations (such as @a) are annotated by @Inherited Meta annotations, the subclass of the class can inherit this annotation @a of the class. Note that this inheritance is an annotation for the class, and if it is a method annotation, you do not need to use @Inherited. Subclasses inherit the annotations of this method while inheriting the methods of the parent class, unless you override the method.
Returning to the @resource annotation, we see that defining an annotation needs tobe decorated with public @ interface, and is @target, @Retention,@Documented (optional),@ Inherited (optional) These four meta annotations are decorated. We can think of annotations as a special class. Look inside the class, define a lot of methods, no access modifiers, no method body, no parameters, only return value types. The return value can have a default value, such as
String name () default "";
String lookup () default "";
< Span style= "COLOR: #0000ff" > class<?> type () default Java.lang.object.class
< Span style= "COLOR: #0000ff" > Span style= "COLOR: #0000ff" >enum AuthenticationType {CONTAINER, application} span>
< Span style= "COLOR: #0000ff" > < Span style= "COLOR: #0000ff" > AuthenticationType AuthenticationType () default Authenticationtype.container;
< Span style= "COLOR: #0000ff" > < Span style= "COLOR: #0000ff" > boolean shareable () Default true
< Span style= "COLOR: #0000ff" > < Span style= "COLOR: #0000ff" > < Span style= "COLOR: #000000" > String mappedname () default "" ; String description () default "" ;
It is important to remember that this method defines the format, no parameters, no method body, in fact, we can understand that some member variables are defined, except that the member variable names are appended with a (), and the default keyword can be used to assign the initial value.
After defining a member variable, we can assign a value to the member variable when using this annotation. such as @resource (name= "Basedao").
PS: If there is only one member in the annotation, and it is called value, we do not have to specify the name of the member when we pass in value. This is the case, for example, @target (elementtype.annotation_type).
3. As far as the information provided from an annotation class itself is concerned, we can only know its purpose (learned from @target meta-annotations), The life cycle (@Retention ), and then know its member variables. In addition to learning the specific role of this annotation from other sources (such as the source comment) and applying it (such as labeling a service class with @service), you cannot see what it does with the definition file of the annotations. We also have limited programming of annotation information, which can be used to obtain the annotation information of a class, a member, or a method, a member value of an annotation, etc. such as the following code.
PackageCom.xdx.learn;ImportJava.lang.annotation.ElementType;Importjava.lang.annotation.Retention;ImportJava.lang.annotation.RetentionPolicy;ImportJava.lang.annotation.Target;//defines an annotation class that can be used for classes and methods@Retention (retentionpolicy.runtime) @Target ({Elementtype.type,elementtype.method}) Public@InterfaceAnno {String value ()default"";} PackageCom.xdx.learn;ImportJava.lang.reflect.Method; @Anno ("Anno") Public classannotest {@Anno ("Anno") Public voidfunc () {System.out.println ("Hello"); } Public Static voidMain (String args[])throwsclassnotfoundexception, nosuchmethodexception, securityexception{Class clz=class.forname ("Com.xdx.learn.AnnoTest"); //reflection Gets the annotation information for a class if(Clz.getannotation (Anno.class)!=NULL) {Anno Anno= (Anno) clz.getannotation (Anno.class); System.out.println (Anno.value ()); System.out.println (Anno.annotationtype ()); } //annotation information for a reflection acquisition methodMethod Method=clz.getdeclaredmethod ("func",NULL); if(Method.isannotationpresent (Anno.class) {Anno Anno=method.getannotation (Anno.class); System.out.println (Anno.value ()); System.out.println (Anno.annotationtype ()); } }}
The result of the above code operation is:
Anno
Interface Com.xdx.learn.Anno
Anno
Interface Com.xdx.learn.Anno
Java Annotation Details