Java反射之深入理解

目录
  • 一、Java反射机制概述
  • 二、理解Class类并获取Class实例
    • 关于java.lang.Class类的理解
  • 三、通过反射创建对应的运行时类的对象(反射的应用1)
  • 四、获取运行时类的完整结构(反射的应用2)
    • 1.获取当前运行时类的属性结构
    • 2.获取运行时类的方法结构
    • 3.获取运行时类的其他结构
  • 五、调用运行时类的指定结构(反射的应用3)

一、Java反射机制概述

//反射之前,对于Person的操作
    @Test
    public void test1(){
        //1.创建Person类的对象
        Person p1 = new Person("Tom",12);
        //2.通过对象,调用其内部的属性、方法
        p1.age = 10;
        System.out.println(p1.toString());//Person{name='Tom', age=10}
        p1.show();//你好,我是一个人
        //在Person类外部,不可以通过Person类的对象调用其内部私有结构。
        //比如:name、showNation()以及私有的构造器
    }
    //反射之后,对于Person的操作
    @Test
    public void test2() throws Exception {
        Class clazz = Person.class;
        //1.通过反射,创建Person类的对象
        Constructor cons = clazz.getConstructor(String.class, int.class);
        Object obj = cons.newInstance("Tom", 12);
        Person p = (Person)obj;
        System.out.println(p.toString());
        //2.通过反射,调用对象指定的属性、方法
        //调用属性
        Field age = clazz.getDeclaredField("age");
        age.set(p,10);
        System.out.println(p.toString());
        //调用方法
        Method show = clazz.getDeclaredMethod("show");
        show.invoke(p);
        System.out.println("*********************************************");
        //通过反射,可以调用Person类的私有结构。比如:私有的构造器、方法、属性
        //调用私有的构造器
        Constructor cons1 = clazz.getDeclaredConstructor(String.class);
        cons1.setAccessible(true);
        Person p1 =(Person) cons1.newInstance("Jerry");
        System.out.println(p1);
        //调用私有的属性
        Field name = clazz.getDeclaredField("name");
        name.setAccessible(true);
        name.set(p1,"HanMeimei");
        System.out.println(p1);
        //调用私有的方法
        Method showNation = clazz.getDeclaredMethod("showNation", String.class);
        showNation.setAccessible(true);
        String nation = (String) showNation.invoke(p1, "中国");//相当于String nation = p1.showNation("中国")
        System.out.println(nation);
    }

疑问1:通过直接new的方式过反射的方式都可以调用公共的结构,开发中到底用那个?
建议:直接new的方式
什么时候后使用:反射的方式?

(反射的特征:动态性)在编译时不能确定要造那个类的对象时,使用反射。
疑问2:反射的机制与面向对象中的封装性是不是矛盾的?如何看待两个技术?
不矛盾。我的理解:开发中,封装性给我们的提示是,私有的属性不建议直接修改,而是通过get、set方法去做。反射给我们的的提示是,不建议直接修该的私有属性,如果非要修改,也是可以通过反射修改的。总结:反射解决的是能不能调用的问题,封装性解决的是建议我们如何掉的问题。

二、理解Class类并获取Class实例

关于java.lang.Class类的理解

//获取Class的实力的方式(前三种方式需要掌握)
    @Test
    public void test3() throws ClassNotFoundException {
        //方式一:调用运行时类的属性:class
        Class clazz1 = Person.class;
        System.out.println(clazz1);//class zx_reflection.Person
        //方式二:通过运行时类的对象,调用getClass()
        Person p1 = new Person();
        Class clazz2 = p1.getClass();
        System.out.println(clazz2);//class zx_reflection.Person
        //方式三:调用Class的静态方法:forName(String classPath)(这种方式常用)
        Class clazz3 = Class.forName("class zx_reflection.Person");
        System.out.println(clazz3);//class zx_reflection.Person
        System.out.println(clazz1 == clazz2);//true
        System.out.println(clazz1 == clazz3);//true
        //方式四:使用类的加载器:ClassLoader(了解)
        ClassLoader classLoader = ReflectionTest.class.getClassLoader();
        Class clazz4 = classLoader.loadClass("class zx_reflection.Person");
        System.out.println(clazz4);
    }
    //Class实例可以时那些结构的说明:
    @Test
    public void test4(){
        Class c1 = Object.class;
        Class c2 = Comparable.class;
        Class c3 = String[].class;
        Class c4 = int[][].class;
        Class c5 = ElementType.class;
        Class c6 = Override.class;
        Class c7 = int.class;
        Class c8 = void.class;
        Class c9 = Class.class;
        int[] a = new int[10];
        int[] b = new int[100];
        Class c10 = a.getClass();
        Class c11 = b.getClass();
        //只要数组的元素类型与维度一样,就是同一个Class
        System.out.println(c10 == c11);//true
    }


1.类的加载的过程:
程序经过javac.exe命令以后,会生成一个或多个字节码文件(.class结尾)。
接着我们使用java.exe命令对某个字节码文件进行解释运行。相当于将某个字节码文件加载到内存中。此过程就称为类的加载。
加载到内存中的类,我们就称为运行时类,此运行时类,就作为Class的一个实例。
2.换句话说,Class的实例就对应着一个加载到内存中的运行时类。
3.加载到内存中的一个运行时类,会缓存一段时间;在此时间之内 ,我们可以通过不同的方式来获取此运行时类。

 @Test
    public void test1(){
        //对于自定义类,使用系统类加载器进行加载
        ClassLoader classLoader = ClassLoaderTest.class.getClassLoader();
        System.out.println(classLoader);//sun.misc.Launcher$AppClassLoader@18b4aac2
        //调用系统类加载器的getParent():获取扩展类加载器
        ClassLoader classLoader1 = classLoader.getParent();
        System.out.println(classLoader1);//sun.misc.Launcher$ExtClassLoader@54bedef2
        //调用扩展类加载器的getParent():无法获取引导类加载器
        //引导类加载器主要负责加载java的核心类库,无法加载自定义类的。
        ClassLoader classLoader2 = classLoader1.getParent();
        System.out.println(classLoader2);//null
        ClassLoader classLoader3 = String.class.getClassLoader();
        System.out.println(classLoader3);//null
    }
    Properties:用来读取配置文件

    @Test
    public void test2() throws Exception {
        Properties pros = new Properties();
        //此时的文件默认在当前的module下
        //读取配置文件的方式一:
//        FileInputStream fis = new FileInputStream("jdbc.properties");
//        pros.load(fis);
        //读取配置文件的方式二:使用ClassLoader
        //配置文件默认识别为:当前module的src下
        ClassLoader classLoader = ClassLoaderTest.class.getClassLoader();
        InputStream is = classLoader.getResourceAsStream("jdbc1.properties");
        pros.load(is);

        String user = pros.getProperty("user");
        String password = pros.getProperty("password");
        System.out.println("user = " + user + ",password" + password);//user = 吴飞,passwordabc123
    }

三、通过反射创建对应的运行时类的对象(反射的应用1)

public class NewInstanceTest {
    @Test
    public void test1() throws IllegalAccessException, InstantiationException {
        Class<Person> clazz = Person.class;
        /*
        newInstance():调用此方法,创建对应的运行时类的对象,内部调用了运行时类的空参构造器
        要想此方法正常的创建运行时类的对象,要求:
        1.运行时类必须提供空参的构造器
        2.空参的构造器的访问权限得够。通常,设置为public

        在javabean中要求提供一个public的空参构造器。原因:
        1.便于通过反射,创建运行时类的对象
        2.便于子类继承此运行时类时,默认调用super()时,保证父类有此构造器
         */
        Person obj = clazz.newInstance();
        System.out.println(obj);//Person{name='null', age=0}
    }
    //体会反射的动态性
    @Test
    public void test2() {
        int num = new Random().nextInt(3);//0,1,2
        String classPath = "";
        switch(num){
            case 0:
                classPath = "java.util.Date";
                break;
            case 1:
                classPath = "java.lang.Object";
                break;
            case 2:
                classPath = "zx_reflection/Person.java";
                break;
            try {
                Object obj = getInstance(classPath);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
    /*
    创建一个指定类的对象
    classPath:指定类的全类名
     */
    public Object getInstance(String classPath) throws Exception {
        Class clazz = Class.forName(classPath);
        return clazz.newInstance();
    }
}

总结:创建类的对象的方式?

方式一:new + 构造器

方式二:要创建Xxx类的对象,可以考虑:Xxx、Xxxs、XxxBuilder类中查看是否有静态方法的存在。可以调用其静态方法,创建Xxx对象。

方式三:通过反射。(使用频率、先后顺序与书写顺序一致)

四、获取运行时类的完整结构(反射的应用2)

1.获取当前运行时类的属性结构

@Test
    public void test1(){
        Class clazz = Person.class;
        //获取属性结构
        //getFields():获取当前运行时及其父类中声明为public访问权限的属性
        Field[] fields = clazz.getFields();
        for(Field f : fields){
            System.out.println(f);
        }
        System.out.println();
        //getDeclaredFields():获取当前运行时类中声明的所有属性。(不包含父类中声明的属性)
        Field[] declaredFields = clazz.getDeclaredFields();
        for(Field f : declaredFields){
            System.out.println(f);
        }
    }
    @Test
    public void test2(){
        Class clazz = Person.class;
        Field[] declaredFields = clazz.getDeclaredFields();
        for(Field f : declaredFields){
            //1.权限修饰符
            int modifiers = f.getModifiers();
            System.out.print(Modifier.toString(modifiers) + "\t");
            //2.数据类型
            Class type = f.getType();
            System.out.print(type.getName() + "\t");
            //3.变量名
            String fName = f.getName();
            System.out.print(fName);
        }
    }

2.获取运行时类的方法结构

 @Test
    public void test1(){
        Class clazz = Person.class;
        //getMethods():获取当前运行时类及所有父类中声明为public权限的方法
        Method[] methods = clazz.getMethods();
        for(Method m : methods){
            System.out.println(m);
        }
        System.out.println();
        //getDeclaredMethods():获取当前运行时类中声明的所有方法。(不包含父类中声明的方法)
        Method[] declaredMethods = clazz.getDeclaredMethods();
        for(Method m : declaredMethods){
            System.out.println(m);
        }
    }
    /*
    @Xxxx
    权限修饰符   返回值类型   方法名(参数类型1 形参名1,...) throws XxxException{}
     */
    @Test
    public void test2(){
        Class clazz = Person.class;
        Method[] declaredMethods = clazz.getDeclaredMethods();
        for(Method m : declaredMethods){
            //1.获取方法声明的注释
            Annotation[] annos = m.getAnnotations();
            for(Annotation a : annos){
                System.out.println(a);
            }
            //2.权限修饰符
            System.out.print(Modifier.toString(m.getModifiers()) + "\t");
            //3.返回值类型
            System.out.print(m.getReturnType().getName() + "\t");
            //4.方法名
            System.out.print(m.getName());
            System.out.print("(");
            //5.形参列表
            Class[] parameterTypes = m.getParameterTypes();
            if(!(parameterTypes == null && parameterTypes.length == 0)){
                for(int i = 0;i < parameterTypes.length;i++){
                    if(i == parameterTypes.length - 1){
                        System.out.println(parameterTypes[i].getName() + "args_" + i);
                        break;
                    }
                    System.out.print(parameterTypes[i].getName() + "args_" + i + ",");
                }
            }
            System.out.print(")");
            //6.抛出的异常
            Class[] exceptionTypes = m.getExceptionTypes();
            if(exceptionTypes.length > 0){
                System.out.print("throws ");
                for(int i = 0;i < exceptionTypes.length;i++){
                    if(i == exceptionTypes.length - 1){
                        System.out.println(exceptionTypes[i].getName());
                        break;
                    }
                    System.out.println(exceptionTypes[i].getName() + ",");
                }
            }
        }
    }

3.获取运行时类的其他结构

 /*
    获取构造器结构
     */
    @Test
    public void test1(){
        Class clazz = Person.class;
        //getConstructors():获取当前运行时类中声明为public的构造器
        Constructor[] constructors = clazz.getConstructors();
        for(Constructor c : constructors){
            System.out.println(c);
        }
        System.out.println();
        //getDeclaredConstructors():获取当前运行时类中声明的所有的构造器
        Constructor[] declaredConstructors = clazz.getDeclaredConstructors();
        for(Constructor c : declaredConstructors){
            System.out.println(c);
        }
    }
    /*
    获取运行时类的父类
     */
    @Test
    public void test2(){
        Class clazz = Person.class;
        Class superclass = clazz.getSuperclass();
        System.out.println(superclass);//class zx_reflection1.Creature
    }
    /*
    获取运行时类的带泛型的父类
     */
    @Test
    public void test3(){
        Class clazz = Person.class;
        Type genericSuperclass = clazz.getGenericSuperclass();
        System.out.println(genericSuperclass);//zx_reflection1.Creature<java.lang.String>
    }
    /*
    获取运行时类的带泛型的父类的泛型
     */
    @Test
    public void test4(){
        Class clazz = Person.class;
        Type genericSuperclass = clazz.getGenericSuperclass();
        ParameterizedType paramType = (ParameterizedType)genericSuperclass;
        //获取泛型类型
        Type[] actualTypeArguments = paramType.getActualTypeArguments();
        System.out.println(actualTypeArguments[0].getTypeName());//java.lang.String
    }
    /*
    获取运行时类实现的接口
     */
    @Test
    public void test5(){
        Class clazz = Person.class;
        Class[] interfaces = clazz.getInterfaces();
        for(Class c : interfaces){
            System.out.println(c);
        }
        System.out.println();
        //获取运行时类的父类实现的接口
        Class[] interfaces1 = clazz.getSuperclass().getInterfaces();
        for(Class c : interfaces1){
            System.out.println(c);
        }
    }
    /*
    获取运行时类所在的包
     */
    @Test
    public void test6(){
        Class clazz = Person.class;
        Package pack = clazz.getPackage();
        System.out.println(pack);//package zx_reflection1
    }
    /*
    获取运行时类声明的注解
     */
    @Test
    public void test7(){
        Class clazz = Person.class;
        Annotation[] annotations = clazz.getAnnotations();
        for(Annotation annos : annotations){
            System.out.println(annos);//@zx_reflection1.MyAnnotation(value=hi)
        }
    }

五、调用运行时类的指定结构(反射的应用3)

@Test
    public void testField() throws Exception {
        Class clazz = Person.class;
        //创建运行时类的对象
        Person p = (Person)clazz.newInstance();
        //获取指定的属性:要求运行时类中属性声明为public(通常不采用此方法,因为属性很少声明为public,常用的在下面)
        Field id = clazz.getField("id");
        /*
        设置当前属性的值
        set():参数1:指明设置那个对象的属性  参数2:将此属性值设置为多少
         */
        id.set(p,1001);
        /*
        获取当前属性的值
        get():参数1:获取那个对象的当前属性值
         */
        int pId = (int)id.get(p);
        System.out.println(pId);
    }
    /*
    如何操作运行时类中的指定的属性----需要掌握
     */
    @Test
    public void testField1() throws Exception {
        Class clazz = Person.class;
        //创建运行时类的对象
        Person p = (Person)clazz.newInstance();
        //1.getDeclaredField(String fieldName):获取运行时类中指定变量名的属性
        Field name = clazz.getDeclaredField("name");
        //2.保证当前属性是可访问的
        name.setAccessible(true);
        //3.获取、设置指定对象的此属性值
        name.set(p,"Tom");
        System.out.println(name.get(p));
    }
    /*
    如何操作运行时类中的指定的方法 -- 需要掌握
     */
    @Test
    public void testMethod() throws Exception {
        Class clazz = Person.class;
        //创建运行时类的对象
        Person p  = (Person)clazz.newInstance();
        /*
        1.获取指定的某个方法
        getDeclaredMethod():参数1:指明获取的方法的名称  参数2:指明获取的方法的形参列表
         */
        Method show = clazz.getDeclaredMethod("show", String.class);
        //2.保证当前方法是可访问的
        show.setAccessible(true);
        /*
        2.调用方法的invoke():参数1:方法的调用者  参数2:给方法形参赋值的实参
        invoke()的返回值即为对应类中调用的方法的返回值
         */
        Object returnValue = show.invoke(p, "CHN");//String nation = p.show()
        System.out.println(returnValue);
        System.out.println("*******************如何调用静态方法*********************************");
        Method showDesc = clazz.getDeclaredMethod("showDesc");
        showDesc.setAccessible(true);
        //如果调用的运行时类中的方法没有返回值,则此invoke()返回null
        Object returnVal = showDesc.invoke(Person.class);
        System.out.println(returnVal);//null
    }
    /*
    如何调用运行时类中的指定的构造器
     */
    @Test
    public void testConstructor() throws NoSuchMethodException {
        Class clazz = Person.class;
        /*
        1.获取指定的构造器
        getDeclaredConstructor():参数:指明构造器的参数列表
         */
        Constructor constructor = clazz.getDeclaredConstructor(String.class);
        //2.保证此构造器是可访问的
        constructor.setAccessible(true);
    }

到此这篇关于Java反射之深入理解的文章就介绍到这了,更多相关Java反射内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

(0)

相关推荐

  • Java 反射(Reflect)详解

    目录 一 首先我们的去知道什么是反射? 二(刨根问底)知道是什么还需要知道什么"成分"组成反射? 2.1 Class 对象的获取及使用 2.2 拿到碗筷就得去盛饭,拿到了Class就得去操作,获得属性 2.3 吃饱饭,我还想学做饭,找到Class,但是我想去获取Class对象的实例. 2.4 调用Class的实例对象的方法 2.5 修改类的私有属性,由于是私有属性,所以需要去关闭程序的安全监测. 三反射的性能 3 .1 走了不同的路,就得比较不同路的对比(性能对比): 四反射的的优缺点

  • Java8 HashMap遍历方式性能探讨

    原因: keySet其实是遍历了2次,一次是转为Iterator对象,另一次是从hashMap中取出key所对应的value.而entrySet只是遍历了一次就把key和value都放到了entry中,效率更高.如果是JDK8,使用Map.foreach方法. 一. keySet和entrySet Map<String, String> map = new HashMap<String, String>(); int num = 5000000; String key, value

  • Java for循环和foreach循环的性能对比分析

    目录 for循环和foreach循环的性能对比 普通for循环语法 foreach 循环语法 for与foreach循环效率比较 对于数组来说 对于链表来说 小结一下吧 for循环和foreach循环的性能对比 在公司codereview过程中,发现一个问题,就是有些人循环用的是普通for循环,有些人用的是foreach循环,它们之间有什么区别?应该在什么时候使用这两种循环了? 两种循环的语法格式: 普通for循环语法 for (int i = 0; i < integers.length; i

  • Java反射及性能详细

    目录 一.准备 二.反射调用流程 1.反射的使用 2.getMethod 和 getDeclaredMethod区别 三.调用反射方法 四.反射效率低的原因 五.反射优化 我们今天不探讨框架层面的内容,暂且认为90%的框架不存在无法容忍的性能问题.在做系统调优的过程中,面对随处可见的invoke调用,我的内心其实是比较抵触的,倒不是说反射怎么不好,对于优雅的源码来说,反射必不可少,个人抵触的原因主要是因为反射把真实的方法"隐藏"的很好,面对长长的线程栈比较头大而已.而且我心里一直有个大

  • Java通过反射来打印类的方法实现

    目录 一. 案例出发 二. 反射方法的分析 2.1 反射的方式 2.2 修饰符的打印 2.3 getDeclaredxxx和getxxx的区别 2.4 getSimpleName和getName有什么不同 工作了有一段时间了,我觉得是时候去复习下Java的一些基础知识,因此写下了这篇文章.平常开发过程中,前端写的比较多,后端也不能忘! 一. 案例出发 先准备一个模板类: public class User { public int id; private String name; public

  • Java反射机制在Spring IOC中的应用详解

    目录 Java反射机制在Spring IOC的应用 下面是Spring通过配置进行实例化对象 Spring的配置如下所示 实现一下Spring底层处理原理 反射机制.反射机制的作用.反射机制的功能 1.反射机制的作用 2.Java反射机制的功能 3.反射机制相关的重要的类有哪些? Java反射机制在Spring IOC的应用 IOC:即"控制反转",不是什么技术,而是一种思想.使用IOC意味着将你设计好的对象交给容器控制,而不是传统的在你的对象内部直接控制. 本篇文章主要讲解一下IOC

  • Java Stopwatch类,性能与时间计时器案例详解

    在研究性能的时候,完全可以使用Stopwatch计时器计算一项技术的效率.但是有时想知道某想技术的性能的时候,又常常想不起可以运用Stopwatch这个东西,太可悲了. 属性: Elapsed 获取当前实例测量得出的总运行时间. ElapsedMilliseconds  获取当前实例测量得出的总运行时间(以毫秒为单位). ElapsedTicks  获取当前实例测量得出的总运行时间(用计时器计时周期表示). IsRunning   获取一个指示 Stopwatch 计时器是否在运行的值. 方法

  • Java反射机制深入理解

    Java反射机制深入理解 一.概念 反射就是把Java的各种成分映射成相应的Java类. Class类的构造方法是private,由JVM创建. 反射是java语言的一个特性,它允程序在运行时(注意不是编译的时候)来进行自我检查并且对内部的成员进行操作.例如它允许一个java的类获取他所有的成员变量和方法并且显示出来.Java 的这一能力在实际应用中也许用得不是很多,但是在其它的程序设计语言中根本就不存在这一特性.例如,Pascal.C 或者 C++ 中就没有办法在程序中获得函数定义相关的信息.

  • Java反射之深入理解

    目录 一.Java反射机制概述 二.理解Class类并获取Class实例 关于java.lang.Class类的理解 三.通过反射创建对应的运行时类的对象(反射的应用1) 四.获取运行时类的完整结构(反射的应用2) 1.获取当前运行时类的属性结构 2.获取运行时类的方法结构 3.获取运行时类的其他结构 五.调用运行时类的指定结构(反射的应用3) 一.Java反射机制概述 //反射之前,对于Person的操作 @Test public void test1(){ //1.创建Person类的对象

  • 关于Java反射机制 你需要知道的事情

    大家都知道,要让Java程序能够运行,那么就得让Java类要被Java虚拟机加载.Java类如果不被Java虚拟机加载,是不能正常运行的.现在我们运行的所有的程序都是在编译期的时候就已经知道了你所需要的那个类的已经被加载了. Java的反射机制是在编译并不确定是哪个类被加载了,而是在程序运行的时候才加载.探知.自审.使用在编译期并不知道的类.这样的特点就是反射. 反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法:对于任意一个对象,都能够调用它的任意一个方法和属性:这种动态

  • 深入理解Java反射

    要想理解反射的原理,首先要了解什么是类型信息.Java让我们在运行时识别对象和类的信息,主要有2种方式:一种是传统的RTTI,它假定我们在编译时已经知道了所有的类型信息:另一种是反射机制,它允许我们在运行时发现和使用类的信息. 1.Class对象 理解RTTI在Java中的工作原理,首先需要知道类型信息在运行时是如何表示的,这是由Class对象来完成的,它包含了与类有关的信息.Class对象就是用来创建所有"常规"对象的,Java使用Class对象来执行RTTI,即使你正在执行的是类似

  • Java反射的应用之动态代理深入理解

    目录 一.代理模式的引入 二.动态代理 一.代理模式的引入 静态代理举例 特点:代理类和被代理类在编译期间,就确定下来了. interface ClothFactory{ void produceCloth(); } //代理类 class ProxyClothFactory implements ClothFactory{ private ClothFactory factory;//用被代理类对象进行实例化 public ProxyClothFactory(ClothFactory fact

  • Java 反射机制的实例详解

    Java 反射机制的实例详解 前言 今天介绍下Java的反射机制,以前我们获取一个类的实例都是使用new一个实例出来.那样太low了,今天跟我一起来学习学习一种更加高大上的方式来实现. 正文 Java反射机制定义 Java反射机制是指在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法:对于任意一个对象,都能够调用它的任意一个方法和属性:这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制. 用一句话总结就是反射可以实现在运行时可以知道任意一个类的属性和方法. 反射

  • java反射深入剖析(推荐)

    本篇文章依旧采用小例子来说明,因为我始终觉的,案例驱动是最好的,要不然只看理论的话,看了也不懂,不过建议大家在看完文章之后,在回过头去看看理论,会有更好的理解. 下面开始正文. [案例1]通过一个对象获得完整的包名和类名 package Reflect; /** * 通过一个对象获得完整的包名和类名 * */ class Demo{ //other codes... } class hello{ public static void main(String[] args) { Demo demo

  • Java反射机制及Method.invoke详解

    JAVA反射机制 JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法:对于任意一个对象,都能够调用它的任意一个方法:这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制. Java反射机制主要提供了以下功能: 在运行时判断任意一个对象所属的类:在运行时构造任意一个类的对象:在运行时判断任意一个类所具有的成员变量和方法:在运行时调用任意一个对象的方法:生成动态代理. 1. 得到某个对象的属性 复制代码 代码如下: public Object get

  • Java 反射机制详解及实例代码

    Java反射详解 本篇文章依旧采用小例子来说明,因为我始终觉的,案例驱动是最好的,要不然只看理论的话,看了也不懂,不过建议大家在看完文章之后,在回过头去看看理论,会有更好的理解. 下面开始正文. [案例1]通过一个对象获得完整的包名和类名 package Reflect; /** * 通过一个对象获得完整的包名和类名 * */ class Demo{ //other codes... } class hello{ public static void main(String[] args) {

  • Java反射学习 getClass()函数应用

    Java反射学习 所谓反射,可以理解为在运行时期获取对象类型信息的操作.传统的编程方法要求程序员在编译阶段决定使用的类型,但是在反射的帮助下,编程人员可以动态获取这些信息,从而编写更加具有可移植性的代码.严格地说,反射并非编程语言的特性,因为在任何一种语言都可以实现反射机制,但是如果编程语言本身支持反射,那么反射的实现就会方便很多. 1,获得类型类 我们知道在Java中一切都是对象,我们一般所使用的对象都直接或间接继承自Object类.Object类中包含一个方法名叫getClass,利用这个方

随机推荐