What is annotation
Annoation: function
- It is not the procedure itself, which can be explained
- It can be read by other programs (such as compiler)
Format: @ comment name can also add some parameter values, for example: (@ supplesswarning (value = "unchecked"))
Scope of use:
It can be attached to package, class, method, field, etc., which is equivalent to adding additional auxiliary information to them. We can access these metadata through reflection mechanism.
Built in annotation
- @0verride overridden comments
- @Deprecated is not recommended for programmers, but it can be used in a better way
- @Supplerswarning suppression warning (with parameters)
public class Test01 extends Object{ //Rewritten annotation @Override public String toString() { return super.toString(); } @Deprecated public static void test(){ System.out.println("Deprecated"); } @SuppressWarnings("all")//Suppression warning public void test02(){ List list = new ArrayList(); } public static void main(String[] args) { test(); } }
Meta annotation
The function of meta annotation is to annotate other annotations. java defines four standard meta annotation types, which are used to describe other annotation types;
These types and the classes they support are in Java You can find (@ Target, @ Retention, @ Documented, @ Inherited) in lang.annotation package
- @Target: used to describe the applicable scope of the annotation
- @Retention: identifies the level at which annotation information needs to be saved and used to describe the annotation life cycle
-
(source < class < **runtime**)
- @Document: note that the annotation will be included in the javadoc
- @Inherited: indicates that the subclass can inherit the annotation in the parent class
Custom annotation:
//Test meta annotation @MyAnnoation public class Test02 { } // Target identifies the scope of the annotation //Define an annotation method to use on the class @Target(value= {ElementType.METHOD,ElementType.TYPE}) //Identifies the level at which the annotation is valid // source < class < runtime @Retention(value = RetentionPolicy.RUNTIME) //Indicates whether our annotation is generated in javadoc @Documented //Annotation that identifies whether the subclass inherits from the parent class @Inherited @interface MyAnnoation{ }
Custom annotation
Keyword: @ interface
When you use @ interface to customize annotations, you automatically inherit Java lang.annotation. Annotataion interface
analysis:
- Format: public @interface annotation name {definition content}
- Each of these methods actually declares an Oh ah parameter
- The name of the method is the name of the parameter
- The return value type is the type of the parameter
- You can set the default value of the parameter through default
- If there is only one parameter, you can use value (generally used)
import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; //Custom annotation public class Test03 { @MyAnnotation2(name = "hua",school = "Chongqing Yitong College") @MyAnnotatiaon3("hua") public void tets(){} } @Target(value={ElementType.METHOD,ElementType.ANNOTATION_TYPE}) @Retention(value= RetentionPolicy.RUNTIME) @interface MyAnnotation2{ //Annotated parameters: parameter type + parameter name () String name() default ""; int age() default 18 ; int id() default -1;//If the default value is - 1, it means that it does not exist. indexof returns - 1 if it cannot be found String[] school() default "Chongqing Yitong College"; } @Target(value={ElementType.METHOD,ElementType.ANNOTATION_TYPE}) @Retention(value= RetentionPolicy.RUNTIME) @interface MyAnnotatiaon3{ //Only value can be omitted String value(); }
Static VS dynamic language
Dynamic language is a kind of language that can change its structure at runtime: for example, new functions, objects and even code can be introduced, existing functions can be deleted or other structural changes.
Main dynamic languages: Object-C, c#, JavaScript, php, Python, etc
function f(){ var x = "var a=3;var b=5;alert(a+b)"; eval(x);//Change the value of x }
Static language: that is, a language with immutable runtime structure. Such as java and c++
However, java can become a "quasi dynamic language" because of its reflection mechanism
Reflection overview
java Reflection
Reflection is the key to java being regarded as a dynamic language. The reflection mechanism allows programs to obtain any unknown internal information with the help of Reflection API during execution, and can directly operate the internal properties and methods of any object.
Class c = Class.forName("String"); public Test02() throws ClassNotFoundException { }
After loading the Class, an object of Class type is generated in the method area of heap memory (a Class has only one Class object), and this object contains complete Class structure information. We can see the structure of the Class through this formation. The object is like a mirror through which you can see the structure of the Class.
- Normal method: import the required "package class" name = "" instantiate through new = "" to obtain the object
- Reflection method: instantiate object = > getClass() method = > get the completed "package class" name
Functions provided by reflection mechanism:
- Determine the class of any object at run time
- Construct an object of any class at run time
- Judge the member variables and methods of any class at run time
- . . . . Get generic information
- . . . . Call the member variables and methods of any object
- . . . . Processing annotations
- . . . . Generate dynamic proxy
Advantages and disadvantages of reflection:
- Advantages: realize dynamic creation and compilation, reflecting great flexibility
- Disadvantages: it has a great impact on performance. Reflection is basically an interpretation operation that tells the JVM that we want it to meet our requirements. Such operations are always slower than performing the same operation directly.
Main API:
- java.lang.Class stands for class
- java.lang.reflect.Method
- java.lang.reflect.Field
- java.lang.reflect.Constructor
Class class
##Get an instance of Class
- Class c = Person.class; Given the specific class, this method is the most safe and reliable and the program performance is the highest when obtained through the class attribute
- Class c = person.getClass(); If a specific class is known, call the getClass () method of the modified instance to obtain the class object
- Class c = Class.forName(“demo01.Student”); If the full name of the class is known, and the class path is obtained through the static method forname(), ClassNotFoundException may be thrown
package com.hua.reflection; //What are the ways to create the test class public class Test02 { public static void main(String[] args) throws ClassNotFoundException { Person person = new Student("student"); System.out.println("This person is:"+person); //Method 1: obtained by object Class c1 = person.getClass(); System.out.println(c1.hashCode()); //Method 2: forName Class c2 = Class.forName("com.hua.reflection.Student"); System.out.println(c2.hashCode()); //Method 3: get by class name Class c3 = Student.class; System.out.println(c3); //Method 4: packing classes of basic built-in types have a TYPE attribute Class c4 = Integer.TYPE; System.out.println(c4); //Method 5: get the type of parent class Class c5 = c1.getSuperclass(); System.out.println(c5); } } class Person{ public String name; public Person() { } public Person(String name){ this.name=name; } @Override public String toString() { return "Person{" + "name='" + name + '\'' + '}'; } } class Student extends Person{ public Student(String name){ this.name=name; } public Student() { } } class Teacher extends Person{ public Teacher(){} public Teacher(String name){ this.name = name; } }
What objects does class have
package com.hua.reflection; import java.lang.annotation.ElementType; public class Test03 { public static void main(String[] args) { Class c1 = Object.class; Class c2 = Comparable.class; //Interface Class c3 = String[].class; Class c4 = int[][].class; Class c5 = Override.class; Class c6 = ElementType.class; Class c7 = Integer.class; Class c8 = void.class; //Empty class Class c9 = Class.class; System.out.println(c1); System.out.println(c2); System.out.println(c3); System.out.println(c4); System.out.println(c5); System.out.println(c6); System.out.println(c7); System.out.println(c8); System.out.println(c9); //As long as the element type is the same as the dimension, it is the same Class int[] a = new int[10]; int[] b = new int[100]; System.out.println(a.getClass()); System.out.println(b.getClass()); } }
Class load memory analysis
Class initialization
package com.hua.reflection; //When will the test class initialize public class Test05 { static { System.out.println("Main Class is loaded"); } public static void main(String[] args) throws ClassNotFoundException { // Active reference //Son son = new Son();//Main class = parent class = child class //Reflection also produces active references //Class.forName("com.hua.reflection.Son");//Main class = parent class = child class //A method that does not generate a reference to a class System.out.println(Son.b); Son[] array =new Son[5];// Array of classes System.out.println(Son.M);//Constant in constant pool } } class Father{ static int b =2; static { System.out.println("The parent class is loaded"); } } class Son extends Father{ static { System.out.println("Subclass loaded"); } static int a = 100; static final int M=1; }
Class loader
The function of class loading: load the bytecode content of the class file into memory, convert these static data into the runtime data structure of the method area, and then generate a Java. Net file representing this class in the heap Lang. class object, as the access entry of class data in the method area.
Class caching: the standard Java se class loader can find classes as required. Once a class is loaded into the class loader, it will be loaded (cached) for a period of time. The jvm garbage collection mechanism can recycle these class objects.
package com.hua.reflection; public class Test06 { public static void main(String[] args) throws ClassNotFoundException { //Gets the loader of the system class ClassLoader systemClassLoader = ClassLoader.getSystemClassLoader(); System.out.println(systemClassLoader); //Gets the parent class loader -- > extension class loader of the system class loader ClassLoader parent = systemClassLoader.getParent(); System.out.println(parent); //Get the parent class loader -- > root loader of the extension class loader (c/c + +) ClassLoader parent1 = parent.getParent(); System.out.println(parent1);//null //Test which loader loads the current class ClassLoader test06 = Class.forName("com.hua.reflection.Test06").getClassLoader(); System.out.println(test06); //Test who loaded the classes built into the jdk test06 = Class.forName("java.lang.Object").getClassLoader(); System.out.println(test06);//null //Get the path where the system class loader can load System.out.println(System.getProperty("java.class.path")); //Parent delegation mechanism: the packages (jar s and classes) created by yourself are found up first. If they are not available, they cannot be used } }
Gets the runtime structure of the class
package com.hua.reflection; import java.lang.reflect.Constructor; import java.lang.reflect.Field; import java.lang.reflect.Method; //Get class information public class Test07 { public static void main(String[] args) throws ClassNotFoundException, NoSuchFieldException, NoSuchMethodException { Class c = Class.forName("com.hua.reflection.user"); //Gets the name of the class System.out.println(c.getName());// Get package name + class name System.out.println(c.getSimpleName());// Get class name user u = new user(); System.out.println(u.getClass().getSimpleName()); for (Field field : c.getDeclaredFields()) {//Get all attribute values of c, filed [] System.out.println(field); } System.out.println("===================================================="); //Gets the value of the specified property System.out.println(c.getDeclaredField("name"));//filed System.out.println("===================================================="); //Method to get class for (Method method : c.getDeclaredMethods()) { System.out.println(method); } System.out.println("===================================================="); //Gets the specified method System.out.println(c.getDeclaredMethod("getName",null)); System.out.println(c.getDeclaredMethod("setName", String.class)); //Gets the specified constructor Constructor[] constructor =c.getConstructors(); for (Constructor constructor1 : constructor) { System.out.println(constructor1); } //Gets the specified constructor System.out.println(c.getConstructor(int.class,String.class,int.class)); } }
Dynamically create object execution methods
Create the object of the class through the newInstance () method
package com.hua.reflection; import java.lang.reflect.Constructor; import java.lang.reflect.Field; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; //Create objects dynamically through reflection public class Test08 { public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException, NoSuchFieldException { Class c = Class.forName("com.hua.reflection.user");//Get class object System.out.println(c); //Construct an object user user = (user)c.newInstance();//Essentially calls the class's parameterless constructor System.out.println(user); //Creating objects through constructors Constructor constructor = c.getDeclaredConstructor(int.class,String.class,int.class); user user1 = (user)constructor.newInstance(001,"hua",10); System.out.println(user1); //Get a method by reflection Method method = c.getDeclaredMethod("setName", String.class); //invoke: the meaning of activation (object, value) method.invoke(user,"Hua"); //user.setAge(10); //System.out.println(user.getAge()); // You can call it directly with an object System.out.println(user.getName()); //Operation properties by reflection Field f = c.getDeclaredField("name"); //We can't directly operate private properties. We need to turn off program security monitoring f.setAccessible(true);//Turn off security monitoring and setAccessible() of property or method f.set(user,"hua"); System.out.println(user.getName()); } }
Performance analysis (setAccess)
package com.hua.reflection; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.nio.file.attribute.UserDefinedFileAttributeView; //Performance analysis problems public class Test09 { //Normal mode call public static void test01(){ User user = new User(); user.setName("hua"); long starttime = System.currentTimeMillis();//start time for (int i = 0; i < 100000000; i++) { user.getName(); } long endtime = System.currentTimeMillis();//End time System.out.println("Ordinary call 1 billion times getName()"+(endtime-starttime)+"ms"); } //Reflection mode call public static void test02() throws NoSuchMethodException, InvocationTargetException, IllegalAccessException { User user = new User(); Class c = user.getClass(); Method method = c.getMethod("setName", String.class); method.invoke(user,"hua"); long starttime = System.currentTimeMillis();//start time for (int i = 0; i < 100000000; i++) { user.getName(); } long endtime = System.currentTimeMillis();//End time System.out.println("Reflection calls 1 billion times getName()"+(endtime-starttime)+"ms"); } //Reflection mode call off detection public static void test03() throws NoSuchMethodException, InvocationTargetException, IllegalAccessException { User user = new User(); Class c = user.getClass(); Method method = c.getMethod("setName", String.class); method.setAccessible(true); method.invoke(user,"hua"); long starttime = System.currentTimeMillis();//start time for (int i = 0; i < 100000000; i++) { user.getName(); } long endtime = System.currentTimeMillis();//End time System.out.println("Reflection call (close detection) 1 billion times getName()"+(endtime-starttime)+"ms"); } public static void main(String[] args) throws InvocationTargetException, NoSuchMethodException, IllegalAccessException { test01();; test02(); test03(); } }
Reflection operation generics
package com.hua.reflection; import java.lang.reflect.AnnotatedType; import java.lang.reflect.Method; import java.lang.reflect.ParameterizedType; import java.lang.reflect.Type; import java.util.List; import java.util.Map; //Get generics through reflection public class Test10 { public void test01(Map<String,User> map, List<User> list){ System.out.println("test01"); } public Map<String,User> test02(){ System.out.println("test02"); return null; } public static void main(String[] args) throws NoSuchMethodException { Method method01 = Test10.class.getMethod("test01", Map.class, List.class); Type[] method01GenericParameterTypes = method01.getGenericParameterTypes(); for (Type method01GenericParameterType : method01GenericParameterTypes) { System.out.println(method01GenericParameterType); if (method01GenericParameterType instanceof ParameterizedType) { Type[] actualTypeArguments = ((ParameterizedType) method01GenericParameterType).getActualTypeArguments(); for (Type actualTypeArgument : actualTypeArguments) { System.out.println(actualTypeArgument); } } } System.out.println("sssssssssssssssssssssssssssssssssssssss"); Method method02 = Test10.class.getMethod("test02", null); Type genericReturnType = method02.getGenericReturnType(); if(genericReturnType instanceof ParameterizedType){ Type[] actualTypeArguments = ((ParameterizedType) genericReturnType).getActualTypeArguments(); for (Type actualTypeArgument : actualTypeArguments) { System.out.println(actualTypeArgument); } } } }
Get annotation information
package com.hua.reflection; import java.lang.annotation.*; import java.lang.reflect.Field; //Practice reflection operation annotation public class Test11 { public static void main(String[] args) throws ClassNotFoundException, NoSuchFieldException { Class c = Class.forName("com.hua.reflection.Student2"); //Get annotations through reflection Annotation[] annotations = c.getAnnotations(); for (Annotation annotation : annotations) { System.out.println(annotation); } //Get the value of annotation value MyAnnoation02 myAnnoation02 = (MyAnnoation02)c.getAnnotation(MyAnnoation02.class); String value = myAnnoation02.value(); System.out.println(value); //Gets the annotation specified by the class Field name = c.getDeclaredField("name"); Filed filed = name.getAnnotation(Filed.class); System.out.println(filed.columnNmae()); System.out.println(filed.type()); System.out.println(filed.length()); } } @MyAnnoation02("db_student") class Student2{ @Filed(columnNmae = "db_id",type = "int",length = 10) private int id; @Filed(columnNmae = "db_age",type = "int",length = 10) private int age; @Filed(columnNmae = "db_name",type = "varchar",length = 10) private String name; public Student2() { } public Student2(int id, int age, String name) { this.id = id; this.age = age; this.name = name; } public int getId() { return id; } public void setId(int id) { this.id = id; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } } //Annotation of class name @Target(ElementType.TYPE) @Retention(RetentionPolicy.RUNTIME) @interface MyAnnoation02{ String value(); } //Attribute annotation @Target(ElementType.FIELD) @Retention(RetentionPolicy.RUNTIME) @interface Filed{ String columnNmae(); String type(); int length(); }