Java programming ideology (15th)-reflection of type information

Source: Internet
Author: User

Java programming ideology (15th)-reflection of type information

After talking about. class and Class, continue.


1) generalized Class reference

Class can also be added to the generic type, and the type check will be performed after being added.


Paste the original words in the book, Class Better than Class, although they are equivalent, Class The advantage is that a non-specific class reference is accidentally or neglected. I don't know what this is?

I understand it later. Actually As a wildcard, it is unknown. if you write a conclusion directly, you cannot write a specific type. The author means that a Class with a generic type is selected for a non-specific version.


The reason for adding the generic type is to provide the type check during compilation. If the operation is incorrect, an error is displayed. However, when using a common Class, it is necessary to wait until it is run.


And this Class , JDK documentation:

T-The type of the class modeled by this ClassObject. For example, the type String.classIs Class . Use Class If the class being modeled is unknown. Is to use the Declaration of generic classes. Including: Interface List
  • Type Parameters:E-The type of elements in this list

    It is also a statement.


    2) transformation syntax

    The syntax added by SE5 for Class reference transformation.

    Class Gun {int price = 1;} class DeathGun extends Gun {int price = 2;} public class TestCast {public static void main (String [] args) {Gun g = new DeathGun (); Class
         
          
    D = DeathGun. class; // The usage type of the generic type does not match // Class
          
           
    Dd = Gun. class; DeathGun gg = d. cast (g); System. out. println (gg. price) ;}} cast source code: public T cast (Object obj) {if (obj! = Null &&! IsInstance (obj) throw new ClassCastException (cannotCastMsg (obj); return (T) obj ;}
          
         

    3) Check Before type conversion

    if(x instanceof TV){  ((TV)x).show();}

    Check the object type. If there is an error during the downward transformation, ClassCastException is thrown, so you must first use instanceOf.


    The equivalence between instaceOf and Class.

    class Father{}class Son extends Father{}public class Test {    static void  test(Object o ){        System.out.println("type: "+o.getClass());        System.out.println("o instanceof Father: "+(o instanceof Father));        System.out.println("o instanceof Son: "+(o instanceof Son));        System.out.println("Father.isInstanceOf(o)"+Father.class.isInstance(o));        System.out.println("Son.isInstanceOf(o)"+Son.class.isInstance(o));        System.out.println("o.getClass()==Father.class:"+(o.getClass()==Father.class));        System.out.println("o.getClass()==Son.class:"+(o.getClass()==Son.class));        System.out.println("o.getClass().equals(Father.class):"+(o.getClass().equals(Father.class)));        System.out.println("o.getClass().equals(Son.class):"+(o.getClass().equals(Son.class)));    }        public static void main(String[] args) {        test(new Father());        test(new Son());    }}result:type: class son.Fathero instanceof Father: trueo instanceof Son: falseFather.isInstanceOf(o)trueSon.isInstanceOf(o)falseo.getClass()==Father.class:trueo.getClass()==Son.class:falseo.getClass().equals(Father.class):trueo.getClass().equals(Son.class):falsetype: class son.Sono instanceof Father: trueo instanceof Son: trueFather.isInstanceOf(o)trueSon.isInstanceOf(o)trueo.getClass()==Father.class:falseo.getClass()==Son.class:trueo.getClass().equals(Father.class):falseo.getClass().equals(Son.class):true

    Instanceof refers to this class? Are you a derived class of this class?


    4) Reflection

    The book is simple, about three pages.

    RTTI: The runtime type information can tell you the specific type of the object. However, this type must be known during compilation so that RTTI can recognize it. That is, during compilation, the compiler must know the class to be processed through RTTI.

    This does not seem to be a limitation, but it is in large-scale programming. during compilation, the program may not be able to know the class to which this object belongs.

    The real difference between RTTI and reflection is: RTTI, which is checked and opened by the compiler during compilation. class file, for reflection ,. class files cannot be obtained during compilation. They are opened and checked during runtime. class file.


    Directly use the example in the book and paste a code:

    Public class ShowMethods {private static String usage = "usage: \ n" + "ShowMethods qualified. class. name \ n "+" To show all methods in class or: \ n "+" ShowMethods qualified. class. name word \ n "+" To search for methods involving 'word' "; private static Pattern p = Pattern. compile ("\ w + \\. "); public static void main (String [] args) {if (args. length <1) {System. out. println (usage); System. exit (0) ;}int lines = 0; try {Class
         C = Class. forName (args [0]); Method [] methods = c. getMethods (); Constructor [] ctors = c. getConstructors (); if (args. length = 1) {for (Method method: methods) System. out. println (p. matcher (method. toString ()). replaceAll (""); for (Constructor: ctors) System. out. println (p. matcher (ctor. toString ()). replaceAll (""); lines = methods. length + ctors. length;} else {// In fact, if the author writes this code, the method match will match. If I use java ShowMe Thods ShowMethods // The original one is extracted, but args [1] is ShowMethods. exactly match the method that comes with ShowMethods, that is, the main method. For (Method method: methods) if (method. toString (). indexOf (args [1])! =-1) {System. out. println (p. matcher (method. toString ()). replaceAll (""); lines ++;} for (Constructor ctor: ctors) if (ctor. toString (). indexOf (args [1])! =-1) {System. out. println (p. matcher (ctor. toString ()). replaceAll (""); lines ++ ;}} catch (ClassNotFoundException e) {System. out. println ("No such class:" + e) ;}}f :\> java ShowMethods ShowMethodspublic static void main (String []) public final native Class getClass () public native int hashCode () public boolean equals (Object) public String toString () public final native void Policy () public final native void policyall () public final native void wait (long) throws InterruptedExceptionpublic final void wait (long, int) throws InterruptedExceptionpublic final void wait () throws InterruptedExceptionpublic ShowMethods ()

    Let's take a look at Matcher's replaceAll method. Unlike String's replaceAll method, the latter has two parameters: one is the content to be replaced and the other is the content to be replaced. The former has only one parameter.

    public String replaceAll(String replacement)
    Replaces every subsequence of the input sequence that matches the pattern with the given replacement string.
    Public class TestString {public static void main (String [] args) {String s = "0898 ((*(*))("; // The regular expression is compiled into Pattern p = Pattern. compile ("\ W"); // p. matcher returns a Matcher object. Matcher's replaceAll method can replace the matched string // With the content in the method parameter. System. out. println (p. matcher (s). replaceAll ("-") ;}} result: 0898 --------
    If the regular expression is not replaced, the result is:

    public static void ShowMethods.main(java.lang.String[])public final native java.lang.Class java.lang.Object.getClass()public native int java.lang.Object.hashCode()public boolean java.lang.Object.equals(java.lang.Object)public java.lang.String java.lang.Object.toString()public final native void java.lang.Object.notify()public final native void java.lang.Object.notifyAll()public final native void java.lang.Object.wait(long) throws java.lang.InterruptedExceptionpublic final void java.lang.Object.wait(long,int) throws java.lang.InterruptedExceptionpublic final void java.lang.Object.wait() throws java.lang.InterruptedExceptionpublic ShowMethods()
    Replace the package name before the class.

    Have you found that the forName result is unknown during compilation? We passed the Class parameter during running. Although such advanced things were not used at the beginning, some things, such as Spring, were found to be in use after learning deeply.


    GetMethods obtains all the common methods of the class, including itself, inherited from the parent class, and implemented from the public method of the interface.

    Another method that getDeclaredMethods obtains is the method declared by the class itself, not only the public method, but also the protected method, or even private method. (At the beginning, I was also very confused. I didn't often emphasize encapsulation. Can private users not be able to see it? How can I get private items directly? In fact, we can see that something has a degree, however, this degree is not a dust, and there are some backdoors ).


    GetConstructors returns the public constructor. After a try, the private constructor is not displayed. As mentioned in the book, it stops and continues to expand:

    I have read the Java reflection tutorials before.


    1. Unknown method call

    public class TestRefl {    public static void main(String[] args) {        UnKnown uk = new UnKnown();        Method m = null;        try {            m = uk.getClass().getMethod("print", new Class
         [0]);                m.invoke(uk);        } catch (NoSuchMethodException | InvocationTargetException| SecurityException  |IllegalAccessException e) {            e.printStackTrace();        }    }}class UnKnown{    public void print(){        System.out.println("haha");    }}
    Previously, I changed the method to private. I found that the method could not be found, but changed to public.


    Ii. Object Creation

    public class TestRefl {    public static void main(String[] args) {       Class c = null;       try {        c = c.forName("son.UnKnown");        System.out.println(c.getName());    } catch (ClassNotFoundException e) {        System.out.println("not found");    }       try {        UnKnown u = (UnKnown) c.newInstance();        u.print();    } catch (InstantiationException e) {        e.printStackTrace();    } catch (IllegalAccessException e) {        e.printStackTrace();    }    }}class UnKnown{   static  void print(){        System.out.println("haha");    }}

    Get the object through the constructor.

    public class TestRefl {    public static void main(String[] args) {        Class c = null;        try {            c = c.forName("son.UnKnown");        } catch (ClassNotFoundException e) {            System.out.println("not found");        }        Constructor
          ct[] = c.getConstructors();        try {            UnKnown u = (UnKnown) ct[0].newInstance();            UnKnown u2 = (UnKnown) ct[1].newInstance(1);            u.print();            u2.print();        } catch (InstantiationException e) {            // TODO Auto-generated catch block            e.printStackTrace();        } catch (IllegalAccessException e) {            // TODO Auto-generated catch block            e.printStackTrace();        } catch (IllegalArgumentException e) {            // TODO Auto-generated catch block            e.printStackTrace();        } catch (InvocationTargetException e) {            // TODO Auto-generated catch block            e.printStackTrace();        }    }}class UnKnown {    public UnKnown() {    }    public UnKnown(int i) {    }    static void print() {        System.out.println("haha");    }}
    The constructor array is ordered. 0 is the constructor without parameters. 1 is the passing parameter. You can directly pass the parameter in the method. Of course, private constructor cannot be obtained.


    When the RTTI and reflection are different, the reflection function can be explained in turn, that is, the runtime checks the object type, and any method of calling the object (both Spring and servlet are used, note that no, we configure the method in xml, and then the attributes will be injected according to xml.) At the same time, we can know the method parameters and attributes.


    Reflection is still very powerful. Next we will introduce a dynamic proxy, a previously abused design pattern.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.