java反射机制及应用分析

反射是java程序开发语言的特质之一,它允许运行中的java程序获取自身的信息,并且可以操作类或对象的内部属性。

当用户使用一个类的时候,应该先知道这个类,而后通过这个类产生实例化对象,但是“反”指的是通过对象找到类。

通过反射,我们可以在运行时获得程序或者程序中每一个类型的成员和成员的值。

java反射框架主要提供以下功能:

1 在运行时判断任意一个对象所属的类

2在运行时构造任意一个类的对象

3在运行时判断任意一个类所具有的成员变量和方法(通过反射甚至可以调用private方法)

4在运行时调用任意一个对象的方法

class Person{}

public class TestDemo{

public static void main(String [] args) throwsException{

Person per = new Person(); // 正 着操作

System.out.println(per.getClass().getName()); // 反射

}

}

getClass()方法返回的对象是Class类的对象。

想要取得这个类的实例化对象,有三种方式:

方式1:通过Object的getClass()方法取得,基本不用;

class Person{}

public class TestDemo{

public static void main(String [] args) throwsException{

Person per = new Person(); // 正 着操作

Class <?> cls = per.getClass(); //取得class对象

Systen.out.println(cls.getName());//反射

}

}

方式2:使用“类.class”取得

class Person{}

public class TestDemo{

public static void main(String [] args) throwsException{

Class <?> cls = Person.class; //取得class对象

Systen.out.println(cls.getName());//反射

}

}

方式3:使用Class类内部定义的一个static方法,使用频繁

class Person{}

public class TestDemo{

public static void main(String [] args) throwsException{

Class <?> cls = Class.fornName(“sai.xuexi.fanshe.peroson”); //取得class对象

Systen.out.println(cls.getName());//反射

}

}

新的问题: 取得clas类对象有什么用处呢?

对于对象的实例化操作之前一直依靠构造方法和关键字new完成,在有了class类对象之后,有有了一种提供对象的实例化方法。

例子:通过反射实例化对象

class Person{

public String toString(){

return "Person Class Instance."

}

}

public class TestDemo{

public static void main(String [] args) throwsException{

Person per = new Person(); // 正 着操作

Class <?> cls = Class.fornName(“sai.xuexi.fanshe.peroson”); //取得class对象

Object obj = cls.newInstance();//实例化对象,和使用关键字new一样

Person per = (person)obj;// 向下转型

Systen.out.println(per));//

}

}

使用反射实例化对象 可以减少耦合。(new是造成耦合的关键元凶)

反射在工厂方法中的使用:

 

interface Fruit{
    public  void eat();
}
class Apple implements  Fruit{
    public  void eat(){
        System.out.print("chipingguo");
    }
};
class Orange implements  Fruit{
    public  void eat(){
        System.out.print("chijuzi");
    }
};
class Factory{
    public static Fruit getInstance(String className){
        Fruit f = null;
        if("apple".equals(className)){
            f = new Apple();
        }
        if ("orange".equals(className)){
            f = new Orange();
        }
        return f;
    }
}
public class Demo{
    public static void mani (String args[]){
        Fruit f = null;
        f =Factory.getInstance("apple");
        f.eat();
    }
}

反射的深入应用:

以上只是利用Class类作为了反射实例化对象的基本应用,但是对于一个实例化对象而言,它需要调用类之中的构造方法,普通方法,属性。

1 调用构造方法:

调用构造方法有2种

方法1 取得一个类的全部构造方法:

public Constructor<?>[] getConstructor() throws SecurityException
方法2 取得一个类指定参数的构造方法:

public Constructor<T>[] getConstructor(Class<?> parameterTypes) throws SecurityException,NoSuchMethodException

方法1的应用:

class Person { 
    public Person() {}
    public Person(String name) {}
    public Person(String name,int age) {}
}
public class TestDemo {
    public static void main(String[] args) throws Exception {
        Class<?> cls = Class.forName("cn.mldn.demo.Person") ; // 取得Class对象
        Constructor<?> cons [] = cls.getConstructors() ; // 取得全部构造
        for(int x = 0; x < cons.length; x++) {
            System.out.println(cons[x]);
        }
    }
}

方法2的应用

class Person { 
        private String name;
        private int age;
        public Person(String name,int age) {
            this.name= name ;
            this.age= age ;
        }
        @Override
        public String toString() {
            return"Person [name="+ name+ ", age="+ age+ "]";
        }
    }
    public class TestDemo {
        public static void main(String[] args) throws Exception {
            Class<?> cls = Class.forName("cn.mldn.demo.Person") ; // 取得Class对象
// 取得指定参数类型的构造方法
            Constructor<?> cons = cls.getConstructor(String.class,int.class) ;
            Object obj = cons.newInstance("张三", 20); // 为构造方法传递参数
            System.out.println(obj);
        }
    }

2 调用普通方法

public  Method [] getMethods() throws SecurityException; //  取得全部方法
// 取得指定方法
public Method getMethod(String name ,class<?> parameterTypes) throws SecurityException,NoSuchMethodException;

//取得一个类里面的全部方法
class Person {
    private String name;
    public void setName(String name) {
        this.name= name;
    }
    public String getName() {
        return name;
    }
}
 public  class  Ceshi{
     public static void main(String args[])throws Exception{
         Class<?> cls = Class.forName("sai.xuexi.person");
         Method md [] =cls .getMethods();
         for (int x =0; x<md.length; x++){
             System.out.print(md[x]);
         }
     }
 }

//取得一个类里面的特定方法
class Person {
    private String name;
    public void setName(String name) {
        this.name= name;
    }
    public String getName() {
        return name;
    }
}
 public  class  Ceshi{
     public static void main(String args[])throws Exception{
         Class<?> cls = Class.forName("sai.xuexi.person");//取得class对象
         Object obj = cls.newInstance(); //实例化对象,没有像person转型
         String attribute ="name" //要调用类之中的属性
         Method setMd = cls.getMethod("set" + initcap(attribute),String.class);//set name
         Method getMd =cls.getMethod("get"+ initcap(attribute)); //get Name
         setMd.invoke(obj,"zhangsan");//等价于 person对象.setName("zhansan")
         System.out.print(getMd.invoke(obj)); //等价于 person对象.getName
     }
     public static String initcap(String str){
         return str.substring(0,1).toUpperCase().concat(str.substring(1));
     }
 }

3调用成员

类之中最后一个组成部分就是成员(Field,也就是属性)

 //取得本类的全部成员:
  public Field[] getDeclaredFields() throws SecurityException;
 //应用
 class Person {
     private String name;
 }
 public class Ceshi {
     public static void main(String[] args) throws Exception {
         Class<?> cls = Class.forName("cn.mldn.demo.Person") ; // 取得Class对象
         Field field [] = cls.getDeclaredFields() ; // 取得全部属性
         for(int x = 0; x < field.length; x++) {
             System.out.println(field[x]);
         }
     }
 }

// 取得指定的成员:
 public Field getDeclaredField(String name) throws NoSuchFieldException, SecurityException;
 //应用
 class Person {
     private String name;
 }
 public class Sai {
     public static void main(String[] args) throws Exception {
         Class<?> cls = Class.forName("cn.mldn.demo.Person"); // 取得Class对象
         Object obj = cls.newInstance(); // 对象实例化属性才会分配空间
         Field nameField = cls.getDeclaredField("name") ; // 找到name属性
         nameField.setAccessible(true) ; // 解除封装了
         nameField.set(obj, "张三") ; // Person对象.name = "张三"
         System.out.println(nameField.get(obj)); // Person对象.name

184









  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
资源包主要包含以下内容: ASP项目源码:每个资源包中都包含完整的ASP项目源码,这些源码采用了经典的ASP技术开发,结构清晰、注释详细,帮助用户轻松理解整个项目的逻辑和实现方式。通过这些源码,用户可以学习到ASP的基本语法、服务器端脚本编写方法、数据库操作、用户权限管理等关键技术。 数据库设计文件:为了方便用户更好地理解系统的后台逻辑,每个项目中都附带了完整的数据库设计文件。这些文件通常包括数据库结构图、数据表设计文档,以及示例数据SQL脚本。用户可以通过这些文件快速搭建项目所需的数据库环境,并了解各个数据表之间的关系和作用。 详细的开发文档:每个资源包都附有详细的开发文档,文档内容包括项目背景介绍、功能模块说明、系统流程图、用户界面设计以及关键代码解析等。这些文档为用户提供了深入的学习材料,使得即便是从零开始的开发者也能逐步掌握项目开发的全过程。 项目演示与使用指南:为帮助用户更好地理解和使用这些ASP项目,每个资源包中都包含项目的演示文件和使用指南。演示文件通常以视频或图文形式展示项目的主要功能和操作流程,使用指南则详细说明了如何配置开发环境、部署项目以及常见问题的解决方法。 毕业设计参考:对于正在准备毕业设计的学生来说,这些资源包是绝佳的参考材料。每个项目不仅功能完善、结构清晰,还符合常见的毕业设计要求和标准。通过这些项目,学生可以学习到如何从零开始构建一个完整的Web系统,并积累丰富的项目经验。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值