栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

Java基础 - 反射篇 - 练习巩固与作业

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Java基础 - 反射篇 - 练习巩固与作业

文章目录

通过反射创建对象

基本介绍案例演示 通过反射访问类中的成员

访问属性

基本介绍案例演示 访问方法

基本介绍案例演示 反射作业练习

通过反射创建对象 基本介绍
    方式一:调用类中的public修饰的无参构造器方式二:调用类中的指定构造器Class类相关方法

newInstance:调用类中的无参构造器,获取对应类的对象getConstructor(class…clazz):根据参数列表,获取对应的构造器对象getDecalaredConstructor(class…clazz):根据参数列表,获取对应的所有构造器对象

    Constructor类相关方法

setAccessible:爆破newInstance(Object…obj):调用构造器 案例演示

    测试1:通过反射创建某类的对象,要求该类中必须有public的无参构造测试2:通过调用某个特定构造器的方式,实现创建某类的对象
package com.taotao.reflection;

import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;


@SuppressWarnings({"all"})
public class ReflecCreateInstance {
    public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException {
        //1.现获取User类的Class对象
        Class aClass = Class.forName("com.taotao.reflection.User");

        //2.通过public的无参构造器创建实例
        Object o = aClass.newInstance();
        System.out.println(o);

        //3.通过public的有参构造器创建实例
        
        //【1】.得到对应的构造器
        Constructor constructor = aClass.getConstructor(String.class);
        //【2】创建实参,并传入实参
        Object tao = constructor.newInstance("tao");
        System.out.println("taotao = " + tao);

        //4.通过【非】public的有参构造器创建实例
        //【1】得到私有的构造器对象
//        Constructor constructor1 = aClass.getConstructor(int.class, String.class); //此方法只能得到public
        Constructor constructor1 = aClass.getDeclaredConstructor(int.class, String.class);
        //【2】创建实例,并传入实参,因为是私有,所以还会报错,所以我们采用“爆破”
        constructor1.setAccessible(true);   //爆破,使用反射可以访问private构造器,反射面前,都是纸老虎
        Object taotao = constructor1.newInstance(20, "刘鸿涛");
        System.out.println("taotao = " + taotao);
    }
}

@SuppressWarnings({"all"})
class User {    //User类
    private int age = 10;
    private String name = "涛涛";

    public User() { //public 无参

    }

    public User(String name) {  //public 有参
        this.name = name;
    }

    private User(int age,String name){  //private 有参
        this.age = age;
        this.name = name;
    }

    @Override
    public String toString() {
        return "User{" +
                "age=" + age +
                ", name='" + name + ''' +
                '}';
    }
}

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-rjqx5VrW-1645953265858)(image-20220227102747966.png)]

通过反射访问类中的成员 访问属性 基本介绍
    根据属性名获取Field对象
Field f = clazzz对象.getDeclaredField(属性名);
    爆破:f.setAccessible(true);//f 是Field访问
f.set(o,值);
syso(f.get(o));
    如果是静态属性,则set和get中的参数o,可以写成null
案例演示
package com.taotao.reflection;

import java.lang.reflect.Field;


@SuppressWarnings({"all"})
public class ReflecAccessProperty {
    public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchFieldException {
        //1.得到Student类对应的Class对象
        Class stuClass = Class.forName("com.taotao.reflection.Student");
        //2.创建对象
        Object o = stuClass.newInstance();  //o的运行类型就是Student
        System.out.println(o.getClass());   //Student
        //3.使用反射得到age 属性对象
        Field age = stuClass.getField("age");
        age.set(o,88); //通过反射来操作属性
        System.out.println(o);  //
        System.out.println(age.get(o)); //返回age属性的值

        //4.使用反射操作name 属性
        Field name = stuClass.getDeclaredField("name");
//        name.set(null,"涛涛");  //因为name是static属性,因此 o 也可以写出null,这样也可以设置
        name.setAccessible(true);   //关闭访问检查
        name.set(o,"涛涛");
        System.out.println(o);
        System.out.println(name.get(o));    //涛涛
        System.out.println(name.get(null)); //获取属性值,要求name是static

    }
}

class Student { //类
    public int age;
    private static String name;

    public Student(){

    }

    public String toString() {
        return "Student [age=" + age + ",name=" + name + "]";
    }
}
访问方法 基本介绍
    根据方法名和参数列表获取列表获取Method方法对象:
Method m = clazz.getDeclaredMethod(方法名,XX.class);
    获取对象:Object o = clazz.newInstance();爆破:m.setAccessible(true);访问:Object returnValue = m.invoke(o,实参列表);注意:如果是静态方法,则invoke的参数o,可以写成null
案例演示
package com.taotao.reflection;

import jdk.nashorn.internal.ir.CallNode;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;


@SuppressWarnings({"all"})
public class ReflecAccessMethod {
    public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException {
        //1.得到Boss类对应的Class对象
        Class bossClass = Class.forName("com.taotao.reflection.Boss");

        //2.创建对象
        Object o = bossClass.newInstance();

        //3.调用public的hi方法(getMethod获得公共的方法)
        //Method hi = bossClass.getMethod("hi"); //ok
        //3.1 得到hi方法对象  (getDeclaredMethod是获得所有方法)
        Method hi = bossClass.getDeclaredMethod("hi",String.class);  //ok
        //3.2 调用
        hi.invoke(o,"涛涛教育");

        //4.调用private static
        //4.1 得到 say方法对象
        Method say = bossClass.getDeclaredMethod("say", int.class, String.class, char.class);
        //4.2 因为此方法是私有的,所以我们需要爆破
        say.setAccessible(true);
        System.out.println(say.invoke(o, 100, "涛涛",'男'));
        //4.3 因为say方法是static的,还可以这样调用
        System.out.println(say.invoke(null,200,"李四",'女'));

        //5.在反射中,如果方法有返回值,同一返回Object,但是他运行类型和方法定义的返回类型一致
        Object reval = say.invoke(null, 300, "王五", '男');
        System.out.println("reval的运行类型 = " + reval.getClass()); //String
    }
}

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);
    }
}
反射作业练习

通过反射修改私有成员变量

    定义PrivateTest类,有私有name属性,并且属性值为hellokitty提供getName的公有方法创建PrivateTest的类,利用Class类得到私有的name属性,修改私有的name属性值,并调用getName()的方法打印name属性值
package com.taotao.reflection.homework;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;


@SuppressWarnings({"all"})
public class Homework01 {
    public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchFieldException, NoSuchMethodException, InvocationTargetException {
        //1.得到student类对应的Class对象
        Class testClass = Class.forName("com.taotao.reflection.homework.PrivateTest");

        //2.创建对象
        Object o = testClass.newInstance();

        //使用反射得到私有属性name,爆破
        Field name = testClass.getDeclaredField("name");
        name.setAccessible(true);
        name.set(o,"taotao");

        //使用反射得到公共方法并调用
        Method method = testClass.getMethod("getName");
        System.out.println(method.invoke(o));

    }
}

@SuppressWarnings({"all"})
class PrivateTest {
    private String name = "hellokitty";
    public String getName(){
        return name;
    }
}

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/750240.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号