• Java 反射机制


    1、java反射机制(名词解释)

      在类的动态运行中,对于任意类,都能通过其路径获取类的所有属性和方法;这种动态获取类属性的功能叫做java的反射机制。

    2、java反射机制的作用

      a、能够判断对象所属的类

      b、能够得到任意类的所有属性和方法

      c、能够构造任意类的对象,能够调用任意对象的方法

          d、生成动态代理(反射机制的动态代理 在后续的java动态代理章节 阐述)

    3、Java API

      

    //获取对象的路径名
    Test test=new Test();
    //取得类对象
    Class<?> testClass=test.getClass();
    Class<?> clazz =Class.forName("java类包的路径");
    Class<?> clazz2=Test.class;
    //获取对象的名字
    String testClassName=testClass.getName();
    //获取Class对象
    Class<?> clazz =Class.forName("java类包的路径");
    //取得父类
    Class<?> parentClass =Clazz.getSuperclass();
    //取得类的所有接口
    Class<?> infes[] =Clazz.getInterfaces();
    //实例化类对象
    Class<?> class1=ClassforName("com.demo.User");
    User user=(User)class1.newInstance();
    //取得类的所有构造器
    Constructor constructors[]=class1.getConstructors();
    //获取类的所有方法
    Method method[] =class1.getMethods();
    //调用类中的方法
    Method method=class1.getMenthod("method1");
    menthod.invoke(class.newInstance());
    //获取属性值
    Field[] fields=class1.getDeclaredFields();//本类
    Field[] fields=class1.getFields();//取得实现的接口或者父类的属性
    //取得权限类型
    int mo =fields[0].getModifiers();
    String priv=Modifier.toString(mo);
    //取得属性类型
    Class<?> type=field[0].getType();
    String typeName=type.getName();
    //操作属性
    Object obj=class1.newInstance();
    class1.getDeclaredFields("xx属性").setAccessible(true).set(obj,"xx新属性");
    

     4、应用实例

    package com.demo;
    
    import java.lang.reflect.Method;
    import java.util.ArrayList;
    
    public class TestRefect {
        public static void main(String[] args) throws Exception, NoSuchMethodException {
            ArrayList list=new ArrayList();
            Class<?> clazz=list.getClass();
            Method method=clazz.getMethod("add", Object.class);
            method.invoke(list, "反射");//运行方法  对象 值
            System.out.println(list.get(0));
        }
    
    }

    //获得并修改数组的信息
    package
    net.xsoftlab.baike; import java.lang.reflect.Array; public class TestReflect { public static void main(String[] args) throws Exception { int[] temp = { 1, 2, 3, 4, 5 }; Class<?> demo = temp.getClass().getComponentType(); System.out.println("数组类型: " + demo.getName()); System.out.println("数组长度 " + Array.getLength(temp)); System.out.println("数组的第一个元素: " + Array.get(temp, 0)); Array.set(temp, 0, 100); System.out.println("修改之后数组第一个元素为: " + Array.get(temp, 0)); } }

    修改数组的大小

    package net.xsoftlab.baike;
    import java.lang.reflect.Array;
    public class TestReflect {
        public static void main(String[] args) throws Exception {
            int[] temp = { 1, 2, 3, 4, 5, 6, 7, 8, 9 };
            int[] newTemp = (int[]) arrayInc(temp, 15);
            print(newTemp);
            String[] atr = { "a", "b", "c" };
            String[] str1 = (String[]) arrayInc(atr, 8);
            print(str1);
        }
        // 修改数组大小
        public static Object arrayInc(Object obj, int len) {
            Class<?> arr = obj.getClass().getComponentType();
            Object newArr = Array.newInstance(arr, len);
            int co = Array.getLength(obj);
            System.arraycopy(obj, 0, newArr, 0, co);
            return newArr;
        }
        // 打印
        public static void print(Object obj) {
            Class<?> c = obj.getClass();
            if (!c.isArray()) {
                return;
            }
            System.out.println("数组长度为: " + Array.getLength(obj));
            for (int i = 0; i < Array.getLength(obj); i++) {
                System.out.print(Array.get(obj, i) + " ");
            }
            System.out.println();
        }
    }

    将反射用于工厂模式

    package net.xsoftlab.baike;
    interface fruit {
        public abstract void eat();
    }
    class Apple implements fruit {
        public void eat() {
            System.out.println("Apple");
        }
    }
    class Orange implements fruit {
        public void eat() {
            System.out.println("Orange");
        }
    }
    class Factory {
        public static fruit getInstance(String ClassName) {
            fruit f = null;
            try {
                f = (fruit) Class.forName(ClassName).newInstance();
            } catch (Exception e) {
                e.printStackTrace();
            }
            return f;
        }
    }
    /**
     * 对于普通的工厂模式当我们在添加一个子类的时候,就需要对应的修改工厂类。 当我们添加很多的子类的时候,会很麻烦。
     * Java 工厂模式可以参考
     * http://baike.xsoftlab.net/view/java-factory-pattern
     * 
     * 现在我们利用反射机制实现工厂模式,可以在不修改工厂类的情况下添加任意多个子类。
     * 
     * 但是有一点仍然很麻烦,就是需要知道完整的包名和类名,这里可以使用properties配置文件来完成。
     * 
     * java 读取 properties 配置文件 的方法可以参考
     * http://baike.xsoftlab.net/view/java-read-the-properties-configuration-file
     * 
     * @author xsoftlab.net
     */
    public class TestReflect {
        public static void main(String[] args) throws Exception {
            fruit f = Factory.getInstance("net.xsoftlab.baike.Apple");
            if (f != null) {
                f.eat();
            }
        }
    }
  • 相关阅读:
    浪漫与苦闷的变奏
    连长和教导员
    怀念的怀念
    springboot 配置 swagger常见版本不匹配问题解决方案
    国家政策与理想导向
    python socket web
    python包源码安装与卸载
    ubuntu安装polipo
    arm交叉编译busybox
    交叉编译python3.9.13
  • 原文地址:https://www.cnblogs.com/hqji/p/6646903.html
Copyright © 2020-2023  润新知