记一次Java反射以及演示在设置暴力反射权限后,如何获取和设置给指定私有的属性赋值

文档底部附上它处反射总结以及暴力反射的演示
说明:以下代码没问题能运行,但还有部分内容没学完,较为潦草。此文分为Person类和reflectDemo2 两个类。

----------------- 代码分割线 ---------------------

package com.itcast.domain;

public class Person {
    private String name;
    private int age;

    public String a;
    protected String b;
    String c;
    private String d;

    public String getD() {
        return d;
    }
    public void setD(String d) {
        this.d = d;
    }

    public Person() {
    }

    public Person(String name, int age, String d) {
        this.name = name;
        this.age = age;
        this.d = d;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    @Override
    public String toString() {
        return "Person{" +
                "name='" + name + '\'' +
                ", age=" + age +
                ", a='" + a + '\'' +
                ", b='" + b + '\'' +
                ", c='" + c + '\'' +
                ", d='" + d + '\'' +
                '}';
    }
}

---------------- 代码分割线 ------------------

package com.itcast.reflect;

import com.itcast.domain.Person;
import java.lang.reflect.Field;
import java.lang.reflect.Method;

//@SuppressWarnings("ALL")
public class reflectDemo2 {
    /**
 * 1、获取成员变量们
     Field[] getFields():获取所有public修饰的成员变量
        返回一个数组包含 Field物体反射的类或接口的 类对象代表所有可访问的公共领域。
    Field getField(String name):获取指定public修饰的成员变量
        返回一个 Field对象反映的类或接口的 类对象表示的指定公共成员。
     Field[] getDeclaredFields():获取所有的变量,不考虑修饰符
     Field[] getDeclaredField(String name):获取指定的变量,要考虑修饰符,即需要进行暴力反射

 * 2、获取构造方法们
 Constructor<T> getConstructor(类<?>... parameterTypes)
 返回一个 Constructor对象反映指定的公共构造函数的 类对象表示的类。
 Constructor<?>[] getConstructors()
 返回一个数组包含 Constructor物体反射所有的 类对象表示的类的公共构造函数。

 Constructor<T> getDeclaredConstructor(类<?>... parameterTypes)
 返回一个 Constructor对象反映指定的构造函数的类或接口的 类对象表示。
 Constructor<?>[] getDeclaredConstructors()
 返回 Constructor物体反射所有的构造函数通过 类对象表示的类中声明一个数组。

 * 3、获取成员方法
 方法 getMethod(String name, 类<?>... parameterTypes)
 返回一个 方法对象反映的类或接口的 类对象表示的指定公共成员方法。
 方法[] getMethods()
 返回一个数组包含 方法物体反射所有的类或接口的 类对象表示的公共方法,包括那些由类或接口的超类和超接口继承的声明。

 方法 getDeclaredMethod(String name, 类<?>... parameterTypes)
 返回一个 方法对象反映指定声明方法的类或接口的 类对象表示。
 方法[] getDeclaredMethods()
 返回一个数组包含 方法物体反射所有声明的方法的类或接口的 类对象,代表包括公众、保护,默认(包)的访问,和私有方法,但不包括继承的方法。

 * 4、获取类名
 String getName()
 */

    public static void main(String[] args) throws Exception {

        //0、获取Person的Class对象
        Class personClass = Person.class;
        /**
         *          * 1、获取成员变量们
         *         Field[] getFields()
         *         Field getField(String name)
         *         Field[] getDeclaredFields()
         *         Field[] getDeclaredFields(String name)
         */
        //1、 Field[] getFields() 获取所有public修饰的成员变量
        Field[] fields = personClass.getFields();
        for (Field field:fields) {
            System.out.println(field);
        }

        System.out.println("----------------");
        Field a = personClass.getField("a");
        //获取变量a的值
        Person p = new Person();
        Object value = a.get(p);
        System.out.println(value);//null
        //设置a的值
        a.set(p,"张三");
        System.out.println(p);//Person{name='null', age=0, a='张三', b='null', c='null', d='null'}

        System.out.println("====================");
        // Field[] getDeclaredFields():获取所有的变量,不考虑修饰符
        Field[] declaredFields = personClass.getDeclaredFields();
        /**
         * for(元素类型t 元素变量x : 遍历对象obj){
         * 引用了x的java语句;
         * }
         */
        for (Field declaredField : declaredFields) {
            System.out.println(declaredFields);
        }

        System.out.println("============");


        Field d =  personClass.getDeclaredField("d");
        //忽略访问权限修饰符的安全检查
        //获取指定的变量,要考虑修饰符,即需要进行暴力反射
        d.setAccessible(true);//设置暴力反射权限
        Object value2 = d.get(p);
        System.out.println(value2);//null

        System.out.println("演示在设置暴力反射权限后,如何获取和设置给指定私有的属性赋值");
        /**
         * 演示在设置暴力反射权限后,如何获取和设置给指定私有的属性赋值
         */
        //获取字节码文件
        Class clazz = Person.class;
        //创建对象
        Object obj = clazz.newInstance();
        //获取方法
        Method getD = personClass.getDeclaredMethod("getD");
        Method setD = personClass.getDeclaredMethod("setD", String.class);
        //设置暴力访问权限
        getD.setAccessible(true);
        setD.setAccessible(true);
        Object getValue4 = setD.invoke(obj,"孤独求败");
        Object value3 = getD.invoke(obj);
        System.out.println(value3);//孤独求败


//         * 2、获取构造方法们
//         Constructor<T> getConstructor(类<?>... parameterTypes)
//         Constructor<?>[] getConstructors()
//
//         Constructor<T> getDeclaredConstructor(类<?>... parameterTypes)
//         Constructor<?>[] getDeclaredConstructors()
//
//         * 3、获取成员方法
//         方法 getMethod(String name, 类<?>... parameterTypes)
//         方法[] getMethods()
//
//         方法 getDeclaredMethod(String name, 类<?>... parameterTypes)
//         方法[] getDeclaredMethods()
//
//         * 4、获取类名
//         String getName()
//
    }

}

链接:https://blog.csdn.net/wildwolf_001/article/details/79726870

本文作者:飞飞吻

本文链接:https://www.cnblogs.com/flyingkisses/p/14716079.html

版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。

posted @   飞飞吻  阅读(306)  评论(0编辑  收藏  举报
点击右上角即可分享
微信分享提示
💬
评论
📌
收藏
💗
关注
👍
推荐
🚀
回顶
收起