Java动态性——反射机制学习笔记

java动态性包括:

  • 反射机制
  • 动态编译
  • 动态执行javascript代码
  • 动态字节码

对动态性的理解

  • 在程序运行过程中(而非编译时),动态地对对象创建及操作

动态语言:

  • python
  • javascript

非动态语言:

  • c语言
  • c++
  • java(虽然不是动态语言,但有一定的动态性)

java反射机制的简单使用例子

自定义注解:

@Target(value = {ElementType.TYPE}) //作用域   类
@Retention(RetentionPolicy.RUNTIME) //保留策略  运行时有效
public @interface Table {
    String value();
}
@Target(value = {ElementType.FIELD}) //作用域   描述域
@Retention(RetentionPolicy.RUNTIME) //保留策略  运行时有效
public @interface AnnoField {
    String colName();
    String type();
    int length();
}

定义一个测试类:

@Table("student")
public class Student {

    @AnnoField(colName="name",type="varchar",length=10)
    private String name;
    @AnnoField(colName="age",type="int",length=3)
    private int age;

    public Student(String name, int age) {
        super();
        this.name = name;
        this.age = age;
    }
    public Student() {
    }
    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;
    }
}

通过反射机制获得类的属性、方法和构造器

@SuppressWarnings("all")
public class TestReflection {
    public static void main(String[] args) {
        try {
            //获得class对象
            Class clazz = Class.forName("com.test.reflection.Student");

            //获取类的属性
            Field[] fs = clazz.getDeclaredFields(); //包括私有的   如果只获得public的  用getFields()
            for(Field f : fs) {
                System.out.println(f);
                AnnoField field = f.getAnnotation(AnnoField.class);//获得属性的注解
                System.out.println("列名:"+field.colName());
            }

            //获得类的方法
            Method[] ms = clazz.getDeclaredMethods(); //获得所有的方法
            for(Method m : ms) {
                System.out.println(m);
            }
            Method m1 = clazz.getDeclaredMethod("setName", String.class);//获得指定的方法 ,第二个参数是区分重载的方法
            System.out.println(m1);

            //获得类的构造器
            Constructor[] cs = clazz.getDeclaredConstructors();
            for(Constructor c : cs) {
                System.out.println(c);
            }

            //获得类的注解
            Annotation[] annos = clazz.getDeclaredAnnotations();
            for(Annotation anno : annos) {
                System.out.println("类的注解"+anno);
            }


        }catch (Exception e) {
        }
    }
}

通过反射机制创建类及操作属性和方法

@SuppressWarnings("all")
public class TestReflection2 {
    public static void main(String[] args) {
        try {
            //获得class对象
            Class clazz = Class.forName("com.test.reflection.Student");

            //通过反射API无参构造创建类
            Student stu1 = (Student) clazz.newInstance();
            //通过反射API有参构造创建类
            Constructor c = clazz.getConstructor(String.class,int.class);
            Student stu2 = (Student) c.newInstance("小明",12);
            System.out.println(stu2.getAge());

            //通过反射API执行方法
            Method m1 = clazz.getMethod("setName", String.class);//先获得方法
            m1.invoke(stu1, "小红");
            System.out.println(clazz.getMethod("getName", null).invoke(stu1, null));

            //通过反射API操作属性
            Field f1 = clazz.getDeclaredField("age");
            f1.setAccessible(true); //跳过安全检查,即可以操作非公有属性了。提高效率的常用方式
            f1.set(stu1, 13);
            System.out.println(stu1.getAge());

        }catch (Exception e) {
        }


    }
}

猜你喜欢

转载自blog.csdn.net/qq_37969433/article/details/80330634