Java之反射爆破操作

您所在的位置:网站首页 java反射什么意思 Java之反射爆破操作

Java之反射爆破操作

2024-07-03 19:37| 来源: 网络整理| 查看: 265

文章目录 一些方法反射爆破创建实例(构造器)反射爆破操作属性反射爆破操作属性共通小作业

一些方法

在这里插入图片描述 首先说一下-getField/Method什么的这种不带Declared只能获取到对应public的属性/方法 只有带Declared可以获取到非public的属性/方法 再看不带s和带s区别 不带s只获取对应的构造器/方法 比如说构造器 getDeclaredConstructor(int.class,String class) 就会获取不管什么修饰符,参数类型为int,String的构造器 下面具体讲解

反射爆破创建实例(构造器)

在这里插入图片描述 注意:普通的Class对象.newInstance()已经弃用 一般现在是通过Class对象获取构造器,然后用 构造器.newInstance来创建对象 说明Constructor有一个方法 就是newInstance(参数),对应的参数填写看构造器

package yuan.hsp.reflection; import java.lang.reflect.Constructor; import java.lang.reflect.InvocationTargetException; //一些反射爆破 @SuppressWarnings({"all"}) public class reBlow { public static void main(String[] args) throws InstantiationException, IllegalAccessException, NoSuchMethodException, SecurityException, IllegalArgumentException, InvocationTargetException { //先获取User的Class对象 Class cls = User.class; //1.通过public无参构造实例 User a =(User) cls.newInstance();//不过这个已经弃用了,最好不要用 User newInstance2 = (User)cls.getDeclaredConstructor().newInstance();//现在一般用这个方法 //先获取无参public然后newInstance System.out.println(newInstance2); //2.通过public的有参构造器创建 Constructor constructor = cls.getConstructor(String.class); // 我们传入的参数,变成对应参数类型的Class对象,才能获取对应的构造器 User bUser=(User) constructor.newInstance("小袁"); System.out.println(bUser); //3.通过非public的有参构造器创建 //只有带Declared的方法才可能获取到非public的,可以看博客的图片在Java之类加载中 //先获取private的constructor Constructor declaredConstructor = cls.getDeclaredConstructor(int.class, String.class); //注意,这里直接newInstance会报错,因为我们调用private的方法它会检测 //所以我们之前学过一个操作,也是提高反射效率的操作 declaredConstructor.setAccessible(true);//这个就叫做爆破,没有这句话会报错 // 这个参数是true会取消反射对象访问调查,所以我们就能在别的类用private属性/方法 //在反射面前,一切都是纸老虎 User cUser=(User)declaredConstructor.newInstance(1,"666"); System.out.println(cUser); } } @SuppressWarnings({"all"}) class User{ private int age; private String name; public User() { } private User(int age,String name){ this.age=age; this.name=name; } public User(String name){//无参public this.name=name; } @Override public String toString() { return "User [age=" + age + ", name=" + name + "]"; } }

在这里插入图片描述

所以我们的爆破就是 把Method/Field/Constructor运用setAccessible(true)方法取消访问调查来获取/修改类中非public的方法/字段/构造器 在这里插入图片描述 之前也是讲过,这个方法也会提高反射效率

反射爆破操作属性

在这里插入图片描述

package yuan.hsp.reflection; import java.lang.reflect.Field; import java.lang.reflect.InvocationTargetException; @SuppressWarnings({"all"}) //反射爆破属性 public class BlowField { public static void main(String[] args) throws InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException, SecurityException, NoSuchFieldException { //1.获取Class类 Class student = Student.class; //2.创建对象 Student newInstance = student.getDeclaredConstructor().newInstance(); //3.使用反射得到age属性对象 //public的可以直接修改操作 Field field = student.getField("age"); field.set(newInstance, 88); System.out.println(newInstance); //4.反射爆破操作name Field field2 = student.getDeclaredField("name"); //还是如果没有取消访问调查,无论对对象进行修改操作,都会出错 System.out.println(field2); field2.setAccessible(true);//加上这句就ok了 // field2.set(newInstance, "小袁");//注意就静态变量的设置方式有多种1.实例对象2.null3.0 field2.set(null, "我"); System.out.println(newInstance); } } @SuppressWarnings({"all"}) class Student{ public int age; private static String name; public Student(){ } @Override public String toString() { return name+" "+age; } }

在这里插入图片描述

反射爆破操作属性

在这里插入图片描述

package yuan.hsp.reflection; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; //爆破方法 @SuppressWarnings({"all"}) public class BlowMeghod { public static void main(String[] args) throws InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException, SecurityException { //获取Class对象 Class boss = boss.class; //创建对象 Object newInstance = boss.getDeclaredConstructor().newInstance(); Method hi = boss.getDeclaredMethod("hi",String.class);//注意,如果方法有参数,在方法名后面就是参数列表对应class对象,不然获取不到 //调用 hi.invoke(newInstance, "6666"); //爆破,调用private static方法 Method declaredMethod = boss.getDeclaredMethod("say", int.class, String.class, char.class); declaredMethod.setAccessible(true); System.out.println(declaredMethod.invoke(null, 2,"个",'c'));//因为是private直接用会报错,要取消一下访问调查 //null可以换成0/对象实例,因为是静态的 //方法.invoke中的返回值默认都是Object打var的话,运行类型就是方法的返回类型 } } @SuppressWarnings({"all"}) class boss{ public int age; private static String name; public boss() { } private static String say(int n,String s,char c) { return n+" "+s+" "+c; } public void hi(String s) { System.out.println("hi"+s); } }

在这里插入图片描述

共通

一.就是修改静态属性/调用静态方法 那个对象占用的部分可以有三个值 1.实例对象2.null3.0 都可以,因为是静态的 二.getDeclared…可以获取所有修饰符修饰的!!!!一般你就写这个带Declared就不会发生逆天错误 get…只能获取public修饰的 三.方法有参数的话 getDeclaredMethod(“方法名”,参数列表第一个对应class对象,参数列表第二个对应class对象,…)才能获取对应方法 四.注意用非public属性/方法/构造器 先爆破! setAccessible(true)

小作业

在这里插入图片描述

package yuan.hsp.reflection; import java.lang.reflect.Field; import java.lang.reflect.InvocationTargetException; //小作业 @SuppressWarnings({"all"}) public class homework { public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException, SecurityException, NoSuchFieldException { //获取Class对象 Class cls = Class.forName("yuan.hsp.reflection.privateTest"); //创建对象实例 privateTest a=(privateTest) cls.getDeclaredConstructor().newInstance(); //获取对应字段 Field field = cls.getDeclaredField("name");//注意,不加Declared是获取不到我们的private的,你就记住加Declared就可以!!! field.setAccessible(true);//爆破一下 System.out.println("修改前"+a.getName()); field.set(a, "666"); System.out.println("修改后"+a.getName()); } } class privateTest{ private String name="hellokitty"; public String getName() { return name; } }

在这里插入图片描述



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3