A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

【黑马程序员济南】Java的反射机制——基础知识总结

摘要: Java的反射机制——基础知识总结这些是黑马程序员java基础入门的一个很重要的内容。今天主要给大家简单讲解一下JJava的反射机制——基础知识总结,以后会慢慢讲解黑马程序员的课程内容!

一、什么是Java的反射
大家都知道,要让Java程序能够运行,那么就得让Java类要被Java虚拟机加载。Java类如果不被Java虚拟机加载,是不能正常运行的。现在我们运行的所有的程序都是在编译期的时候就已经知道了你所需要的那个类的已经被加载了。
Java的反射机制是在编译并不确定是哪个类被加载了,而是在程序运行的时候才加载、探知、自审。使用在编译期并不知道的类。这样的特点就是反射。


二、反射机制的作用
在Java运行时环境中,对于任意一个类,可以知道这个类有哪些属性和方法。对于任意一个对象,可以调用它的任意一个方法。这种动态获取类的信息以及动态调用对象的方法的功能来自于Java 语言的反射(Reflection)机制。简单的来说,反射机制指的是程序在运行时能够获取自身的信息。在java中,只要给定类的名字,那么就可以通过反射机制来获得类的所有信息。


三、哪里用到反射机制
有些时候,我们用过一些知识,但是并不知道它的专业术语是什么,在刚刚学jdbc时用过一行代码,Class.forName("com.mysql.jdbc.Driver.class").newInstance();但是那时候只知道那行代码是生成驱动对象实例,并不知道它的具体含义。听了反射机制这节课后,才知道,原来这就是反射,现在很多开框架都用到反射机制,hibernate、struts都是用反射机制实现的。
IDE中当我们构建出一个对象的时候,去调用该对象的方法和属性的时候。一按点,编译工具就会自动的把该对象能够使用的所有的方法和属性全部都列出来,供用户进行选择。这就是利用了Java反射的原理,是对我们创建对象的探知、自审。其他例如Spring框架:IOC(控制反转);Hibernate框架:关联映射等;白盒测试等


四、反射机制的优点与缺点
为什么要用反射机制?直接创建对象不就可以了吗,这就涉及到了动态与静态的概念,
静态编译:在编译时确定类型,绑定对象,即通过。
动态编译:运行时确定类型,绑定对象。动态编译最大限度发挥了java的灵活性,体现了多态的应用,有以降低类之间的藕合性。
优点
(1)能够运行时动态获取类的实例,大大提高系统的灵活性和扩展性。
(2)与Java动态编译相结合,可以实现无比强大的功能
缺点:
(1)使用反射的性能较低,使用反射基本上是一种解释操作,我们可以告诉JVM,我们希望做什么并且它满足我们的要求。这类操作总是慢于只直接执行相同的操作。
(2)使用反射相对来说不安全
(3)破坏了类的封装性,可以通过反射获取这个类的私有方法和属性
所以什么时候使用反射,就要靠业务的需求、大小,以及经验的积累来决定。


五、反射机制的功能
首先Java 反射机制主要提供了以下功能
在运行时判断任意一个对象所属的类。 在运行时构造任意一个类的对象。 在运行时判断任意一个类所具有的成员变量和方法。 在运行时调用任意一个对象的方法
反射的常用类和函数:Java反射机制的实现要借助于4个类:Class,Constructor,Field,Method;
其中class代表的是类对象,Constructor-类的构造器对象,Field-类的属性对象,Method-类的方法对象,
通过这四个对象我们可以粗略的看到一个类的各个组成部分。其中最核心的就是java.lang.Class这个类。它是Java反射机制的起源、基础。当一个类被加载以后,Java虚拟机就会自动产生一个Class对象。通过这个Class对象我们就能获得加载到虚拟机当中这个Class对象对应的方法、成员以及构造方法的声明和定义等信息。应用反射时我们最关心的一般是一个类的构造器、属性和方法,下面我们主要介绍Class类中针对这三个元素的方法:
1、得到构造器的方法 Constructor getConstructor(Class[] params) -- 获得使用特殊的参数类型的公共构造函数, Constructor[] getConstructors() -- 获得类的所有公共构造函数 Constructor getDeclaredConstructor(Class[] params) -- 获得使用特定参数类型的构造函数(与接入级别无关) Constructor[] getDeclaredConstructors() -- 获得类的所有构造函数(与接入级别无关)
2、获得字段信息的方法
Field getField(String name) -- 获得命名的公共字段 Field[] getFields() -- 获得类的所有公共字段 Field getDeclaredField(String name) -- 获得类声明的命名的字段 Field[] getDeclaredFields() -- 获得类声明的所有字段
3、获得方法信息的方法
Method getMethod(String name, Class[] params) -- 使用特定的参数类型,获得命名的公共方法 Method[] getMethods() -- 获得类的所有公共方法 Method getDeclaredMethod(String name, Class[] params) -- 使用特写的参数类型,获得类声明的命名的方法 Method[] getDeclaredMethods() -- 获得类声明的所有方法
在程序开发中使用反射并结合属性文件,可以达到程序代码与配置文件相分离的目的,如果我们想要得到对象的信息,一般需要“引入需要的‘包.类’的名称——通过new实例化——取得实例化对象”这样的过程。使用反射就可以变成“实例化对象——getClass()方法——得到完整的‘包.类’名称”这样的过程。正常方法是通过一个类创建对象,反射方法就是通过一个对象找到一个类的信息。


六、如何运用反射机制
1、使用反射机制的步骤:
导入java.lang.relfect 包
遵循三个步骤
第一步是获得你想操作的类的 java.lang.Class 对象
第二步是调用诸如 getDeclaredMethods 的方法
第三步使用 反射API 来操作这些信息
2、获得Class对象的方法
1)如果一个类的实例已经得到,你可以使用
【Class c = 对象名.getClass(); 】
例: TextField t = new TextField();
Class c = t.getClass();
Class s = c.getSuperclass();
2)如果你在编译期知道类的名字,你可以使用如下的方法
Class c = java.awt.Button.class; 或者Class c = Integer.TYPE;
3)如果类名在编译期不知道, 但是在运行期可以获得, 你可以使用下面的方法
Class c = Class.forName(strg);
这样获得Class类对象的方法,其实是利用反射API把指定字符串的类加载到内存中,所以也叫类加载器加载方法。此时类加载器会把该类的静态方法和静态属性,以及静态代码全部加载到内存中。但此时类的对象还没有产生。所以这就是为什么静态方法不能访问非静态属性和方法。因为静态方法和属性产生的时机在非静态属性和方法之前。
其实在学习java过程Java的反射机制还是比较容易,如果大家想学习java基础的知识,欢迎大家可以去传智播客官网http://www.itheima.com/去了解java基础知识!



0 个回复

您需要登录后才可以回帖 登录 | 加入黑马