java反射获取类的所有成员变量(本类和基类)

我们知道在Java的反射机制中,最核心的一个类就是Class类。

Class类中提供了两个常用的获取类的成员变量的方法。

方法1 getFields()

/**
 * Returns an array containing {@code Field} objects reflecting all
 * the accessible public fields of the class or interface represented by
 * this {@code Class} object.
 *
 * <p> If this {@code Class} object represents a class or interface with no
 * no accessible public fields, then this method returns an array of length
 * 0.
 *
 * <p> If this {@code Class} object represents a class, then this method
 * returns the public fields of the class and of all its superclasses.
 *
 * <p> If this {@code Class} object represents an interface, then this
 * method returns the fields of the interface and of all its
 * superinterfaces.
 *
 * <p> If this {@code Class} object represents an array type, a primitive
 * type, or void, then this method returns an array of length 0.
 *
 * <p> The elements in the returned array are not sorted and are not in any
 * particular order.
 *
 * @return the array of {@code Field} objects representing the
 *         public fields
 * @throws SecurityException
 *         If a security manager, <i>s</i>, is present and
 *         the caller‘s class loader is not the same as or an
 *         ancestor of the class loader for the current class and
 *         invocation of {@link SecurityManager#checkPackageAccess
 *         s.checkPackageAccess()} denies access to the package
 *         of this class.
 *
 * @since JDK1.1
 * @jls 8.2 Class Members
 * @jls 8.3 Field Declarations
 */
@CallerSensitive
public Field[] getFields() throws SecurityException {
    checkMemberAccess(Member.PUBLIC, Reflection.getCallerClass(), true);
    return copyFields(privateGetPublicFields(null));
}

从注释上可以看出来,这个方法是用来获取一个类和其所有父类中被public修饰符修饰的成员变量的。

方法2 getDeclaredFields()

/**
 * Returns an array of {@code Field} objects reflecting all the fields
 * declared by the class or interface represented by this
 * {@code Class} object. This includes public, protected, default
 * (package) access, and private fields, but excludes inherited fields.
 *
 * <p> If this {@code Class} object represents a class or interface with no
 * declared fields, then this method returns an array of length 0.
 *
 * <p> If this {@code Class} object represents an array type, a primitive
 * type, or void, then this method returns an array of length 0.
 *
 * <p> The elements in the returned array are not sorted and are not in any
 * particular order.
 *
 * @return  the array of {@code Field} objects representing all the
 *          declared fields of this class
 * @throws  SecurityException
 *          If a security manager, <i>s</i>, is present and any of the
 *          following conditions is met:
 *
 *          <ul>
 *
 *          <li> the caller‘s class loader is not the same as the
 *          class loader of this class and invocation of
 *          {@link SecurityManager#checkPermission
 *          s.checkPermission} method with
 *          {@code RuntimePermission("accessDeclaredMembers")}
 *          denies access to the declared fields within this class
 *
 *          <li> the caller‘s class loader is not the same as or an
 *          ancestor of the class loader for the current class and
 *          invocation of {@link SecurityManager#checkPackageAccess
 *          s.checkPackageAccess()} denies access to the package
 *          of this class
 *
 *          </ul>
 *
 * @since JDK1.1
 * @jls 8.2 Class Members
 * @jls 8.3 Field Declarations
 */
@CallerSensitive
public Field[] getDeclaredFields() throws SecurityException {
    checkMemberAccess(Member.DECLARED, Reflection.getCallerClass(), true);
    return copyFields(privateGetDeclaredFields(false));
}

从注释上可以看出来,这个方法是用来获取一个类中的所有成员变量的,即包括被public、protected、defautl和private修饰符修饰的所有成员变量。

但是这个方法,其基类的一个成员变量都不会拿得到。

取本类和基类的所有成员变量

要取本类和基类的所有成员变量,Class类中提供的两种获取类中成员变量的方法都不能直接实现这个需求,但是可以通过简单的while循环来实现。

// 取所有字段(包括基类的字段)
Field[] allFields = clazz.getDeclaredFields();
Class superClass = clazz.getSuperclass();
while (superClass != null) {
  Field[] superFileds = superClass.getDeclaredFields();
  allFields = ArrayUtils.addAll(allFields, superFileds);
  superClass = superClass.getSuperclass();
}

这样就取到了类中的所有成员变量,包括基类的成员变量。

"父爱无声,但它一直都在。"

原文地址:https://www.cnblogs.com/yanggb/p/11848524.html

时间: 2024-08-08 03:59:15

java反射获取类的所有成员变量(本类和基类)的相关文章

java 反射 - 获取成员变量的值.

通过反射,可以获取所有声明的成员变量(包括所有的),代码如下: package spt.test.src; public class Person { private String name = "pri_name"; public String id; } 运行测试: package spt.test; import java.lang.reflect.Field; import spt.test.src.Person; class ReflectionTest { @Suppres

Java反射获取类和对象信息全解析

反射可以解决在编译时无法预知对象和类是属于那个类的,要根据程序运行时的信息才能知道该对象和类的信息的问题. 在两个人协作开发时,你只要知道对方的类名就可以进行初步的开发了. 获取类对象 Class.forName(String clazzName)静态方法 调用类的class属性,Person.class返回的就是Person的class对象(推荐使用) 调用某个对象的getClass()方法 具体使用还是要根据实际来选择,第一种方式是比较自由的,只要知道一个类名就可以了,其不会做该类是否存在的

java中获取系统属性以及环境变量

java中获取系统属性以及环境变量 System.getEnv()和System.getProperties()的差别 从概念上讲,系统属性 和环境变量 都是名称与值之间的映射.两种机制都能用来将用户定义的信息传递给 Java 进程.环境变量产生很多其它的全局效应,由于它们不仅对Java 子进程可见,并且对于定义它们的进程的全部子进程都是可见的.在不同的操作系统上,它们的语义有细微的区别,比方,不区分大写和小写.由于这些原因,环境变量更可能有意料不到的副作用.最好在可能的地方使用系统属性.环境变

07_面向对象(成员变量和局部变量区别、类作为形式参数的问题、匿名对象、封装、private关键字、this关键字、构造方法、成员方法、static关键字、静态变量和成员变量、main方法)_02

7:构造方法(掌握)    (1)作用:用于对对象的数据进行初始化    (2)格式:        A:方法名和类名相同        B:没有返回值类型,连void都不能有        C:没有返回值                思考题:构造方法中可不可以有return语句呢?        可以.而是我们写成这个样子就OK了:return;        其实,在任何的void类型的方法的最后你都可以写上:return;    (3)构造方法的注意事项        A:如果我们没写构

Java反射获取对象VO的属性值(通过Getter方法)

有时候,需要动态获取对象的属性值. 比如,给你一个List,要你遍历这个List的对象的属性,而这个List里的对象并不固定.比如,这次User,下次可能是Company. e.g. 这次我需要做一个Excel导出的工具类,导出的批量数据是以List类型传入的,List里的对象自然每次都不同,这取决于需要导出什么信息. 为了使用方便,将对象的属性名与属性值存于Map当中,使用时就可以直接遍历Map了. 此次的思路是通过反射和Getter方法取得值,然后记录在一个Map当中. Kick start

Java基础学习-extends继承(成员变量,局部变量,成员方法)

package extend; /*面向对象-继承: * 多个类的共同成员变量和成员方法.抽取到另一个类中(父类),我们多个类就可以访问到父类的成员了 * */ class Game{ String name; double vesion;//版本号 String agent;//代理商 public void start() { System.out.println("游戏启动"); } public void stop() { System.out.println("游戏

Java反射获取class对象的三种方式,反射创建对象的两种方式

Java反射获取class对象的三种方式,反射创建对象的两种方式 1.获取Class对象 在 Java API 中,提供了获取 Class 类对象的三种方法: 第一种,使用 Class.forName 静态方法. 前提:已明确类的全路径名. 第二种,使用 .class 方法. 说明:仅适合在编译前就已经明确要操作的 Class 第三种,使用类对象的 getClass() 方法. 适合有对象示例的情况下 package com.reflection; /** * Created by Liuxd

如何初始化类的static成员变量?

类的static成员变量不被某一个对象所独有,而是被所有同类型的对象所共有. 只能在头文件中声明类的static成员变量,不可在头文件中初始化,否则会造成重定义.必须在另外一个.cpp文件中进行初始化.并且,初始化的时候不可以有static修饰词. [email protected]:~/project/test/static-test/static2_cpp$ cat static.h #ifndef STATIC_H #define STATIC_H #include<iostream>

学习IOS开问题篇--类中的成员变量如果不实例化是什么情况

@interface Person : NSObject @property (noatonmic,copy) NSString * name; @end 一个person类,name是person得成员变量 如果在一个类中写入person为成员变量 self.person.name = @"zhangsan"; 如果前面不将person实例化,实际上是在对一个空指针进行操作 [nil setname:@"zhangsan"]; 因为oc中对空指针发消息不会报错,所