java反射基础

1、获得Class对象

方法有三种
(1)
使用Class类的forName静态方法:

1

2

3

4

5

 publicstatic Class<?> forName(String className)

```

JDBC开发中常用此方法加载数据库驱动:

```java

 Class.forName(driver);

(2)直接获取某一个对象的class,比如:

1

2

Class<?> klass = int.class;

Class<?> classInt = Integer.TYPE;

(3)调用某个对象的getClass()方法,比如:

1

2

StringBuilder str = new StringBuilder("123");

Class<?> klass = str.getClass();

2、判断是否为某个类的实例

一般地,我们用instanceof关键字来判断是否为某个类的实例。同时我们也可以借助反射中Class对象的isInstance()方法来判断是否为某个类的实例,它是一个Native方法:

1

publicnativebooleanisInstance(Object obj);

3、创建实例

通过反射来生成对象主要有两种方式。
1)使用Class对象的newInstance()方法来创建Class对象对应类的实例。

1

2

Class<?> c = String.class;

Object str = c.newInstance();

2)先通过Class对象获取指定的Constructor对象,再调用Constructor对象的newInstance()方法来创建实例。这种方法可以用指定的构造器构造类的实例。

1

2

3

4

5

6

7

//获取String所对应的Class对象

Class<?> c = String.class;

//获取String类带一个String参数的构造器

Constructor constructor = c.getConstructor(String.class);

//根据构造器创建实例

Object obj = constructor.newInstance("23333");

System.out.println(obj);

4、获取方法

获取某个Class对象的方法集合,主要有以下几个方法:
getDeclaredMethods()
方法返回类或接口声明的所有方法,包括公共、保护、默认(包)访问和私有方法,但不包括继承的方法。

1

public Method[] getDeclaredMethods() throws SecurityException

getMethods()方法返回某个类的所有公用(public)方法,包括其继承类的公用方法。

1

public Method[] getMethods() throws SecurityException

getMethod方法返回一个特定的方法,其中第一个参数为方法名称,后面的参数为方法的参数对应Class的对象

1

public Method getMethod(String name, Class<?>... parameterTypes)

只是这样描述的话可能难以理解,我们用例子来理解这三个方法:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

package org.ScZyhSoft.common;

import java.lang.reflect.InvocationTargetException;

import java.lang.reflect.Method;

publicclasstest1{

                    publicstaticvoidtest()throws IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException {

                            Class<?> c = methodClass.class;

                            Object object = c.newInstance();

                            Method[] methods = c.getMethods();

                            Method[] declaredMethods = c.getDeclaredMethods();

                            //获取methodClass类的add方法

                            Method method = c.getMethod("add", int.class, int.class);

                            //getMethods()方法获取的所有方法

                            System.out.println("getMethods获取的方法:");

                            for(Method m:methods)

                                System.out.println(m);

                            //getDeclaredMethods()方法获取的所有方法

                            System.out.println("getDeclaredMethods获取的方法:");

                            for(Method m:declaredMethods)

                                System.out.println(m);

                        }

    }

classmethodClass{

    publicfinalint fuck = 3;

    publicintadd(int a,int b){

        return a+b;

    }

    publicintsub(int a,int b){

        return a+b;

    }

}

程序运行的结果如下:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

getMethods获取的方法:

public int org.ScZyhSoft.common.methodClass.add(int,int)

public int org.ScZyhSoft.common.methodClass.sub(int,int)

public final void java.lang.Object.wait() throws java.lang.InterruptedException

public final void java.lang.Object.wait(long,int) throws java.lang.InterruptedException

public final native void java.lang.Object.wait(long) throws java.lang.InterruptedException

public boolean java.lang.Object.equals(java.lang.Object)

public java.lang.String java.lang.Object.toString()

public native int java.lang.Object.hashCode()

public final native java.lang.Class java.lang.Object.getClass()

public final native void java.lang.Object.notify()

public final native void java.lang.Object.notifyAll()

getDeclaredMethods获取的方法:

public int org.ScZyhSoft.common.methodClass.add(int,int)

public int org.ScZyhSoft.common.methodClass.sub(int,int)

可以看到,通过getMethods()获取的方法可以获取到父类的方法,比如java.lang.Object下定义的各个方法。

5、获取构造器信息

获取类构造器的用法与上述获取方法的用法类似。主要是通过Class类的getConstructor方法得到Constructor类的一个实例,而Constructor类有一个newInstance方法可以创建一个对象实例:

1

public T newInstance(Object ... initargs)

此方法可以根据传入的参数来调用对应的Constructor创建对象实例~

6、获取类的成员变量(字段)信息

主要是这几个方法,在此不再赘述:
getFiled: 访问公有的成员变量
getDeclaredField:所有已声明的成员变量。但不能得到其父类的成员变量
getFileds
getDeclaredFields用法同上(参照Method

7、调用方法

当我们从类中获取了一个方法后,我们就可以用invoke()方法来调用这个方法。invoke方法的原型为:

1

2

3

public Object invoke(Object obj, Object... args)

        throws IllegalAccessException, IllegalArgumentException,

           InvocationTargetException

下面是一个实例:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

publicclasstest1{

    publicstaticvoidmain(String[] args)throws IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException {

        Class<?> klass = methodClass.class;

        //创建methodClass的实例

        Object obj = klass.newInstance();

        //获取methodClass类的add方法

        Method method = klass.getMethod("add",int.class,int.class);

        //调用method对应的方法 => add(1,4)

        Object result = method.invoke(obj,1,4);

        System.out.println(result);

    }

}

classmethodClass{

    publicfinalint fuck = 3;

    publicintadd(int a,int b){

        return a+b;

    }

    publicintsub(int a,int b){

        return a+b;

    }

}

关于invoke()方法的详解,后面我会专门写一篇文章来深入解析invoke的过程。

8、利用反射创建数组

数组在Java里是比较特殊的一种类型,它可以赋值给一个Object Reference。下面我们看一看利用反射创建数组的例子:

1

2

3

4

5

6

7

8

9

10

11

12

publicstaticvoidtestArray()throws ClassNotFoundException {

        Class<?> cls = Class.forName("java.lang.String");

        Object array = Array.newInstance(cls,25);

        //往数组里添加内容

        Array.set(array,0,"hello");

        Array.set(array,1,"Java");

        Array.set(array,2,"fuck");

        Array.set(array,3,"Scala");

        Array.set(array,4,"Clojure");

        //获取某一项的内容

        System.out.println(Array.get(array,3));

    }

其中的Array类为java.lang.reflect.Array类。我们通过Array.newInstance()创建数组对象,它的原型是:

1

2

3

4

publicstatic Object newInstance(Class<?> componentType, int length)

        throws NegativeArraySizeException {

        return newArray(componentType, length);

    }

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值