您的位置:首页 > 数据库 > Oracle

java中的反射 2.1——类:获取类对象@译自Oracle官方文档

2015-07-22 16:46 525 查看
译自:http://docs.oracle.com/javase/tutorial/reflect/class/classNew.html
java.lang.Class类是所有反射操作的切入点。除java.lang.reflect.ReflectPermission类外,所有的java.lang.reflect包中的类都没有公共构造函数。要使用这些类就需要借助Class类中的特定方法。有许多种方法获取一个Class,这些方法的不同之处在于当前可以访问到的是一个对象(object)、是一个类(class)的名字还是一个已经存在的类。

Object.getClass()

如果已经有一个对象的实例,那么获取它的Class最简单的方法就是调用Object.getClass()。这个方法当然只适用于继承自Object的引用类型。例子:

Class c = "foo".getClass();


返回String的Class。

Class c = System.console().getClass();


静态方法System.console返回虚拟机中唯一的控制台(console),而getClass()返回的是java.io.Console对应的Class。

enum E { A, B }
Class c = A.getClass();


A是枚举类型E的一个实例;因此getClass()返回的是枚举类型E对应的Class。

byte[] bytes = new byte[1024];
Class c = bytes.getClass();


由于数组也是对象,所以也可以对一个数组的实例调用getClass()。返回的是byte类型数组对应的Class。

import java.util.HashSet;
import java.util.Set;

Set<String> s = new HashSet<String>();
Class c = s.getClass();


在这个例子中,java.util.Set是java.util.HashSet类型对象的接口。getClass()返回的是java.util.HashSet对应的Class。

.class语法

如果一种类型是可用的但我们并没有它的实例。那么可以在类型后边加后缀“.class”来获取Class。这也是获取一个基本类型(比如int,char)的Class最简单的方法

boolean b;
Class c = b.getClass();   // 编译错误

Class c = boolean.class;  // 正确的写法


注意
boolean.getClass()
语句会造成编译错误因为boolean是一个基本类型因此不能被间接引用(dereferenced)。应该使用.class语法来返回boolean对应的Class。

Class c = java.io.PrintStream.class;


变量c被声明为一个java.io.PrintStream对应的Class。

Class c = int[][][].class;


.class语法也可用于获取一个多维数组的Class。

Class.forName()

如果可以得到一个类的完全限定名称(fully-qualified
name),那么就可以使用静态方法Class.forName()来获取对应的Class。这种方法不能用于基本类型。要获得一个数组类型的完全限定名称可以使用Class.getName()。

Class c = Class.forName("com.duke.MyLocaleServiceProvider");


这过语句会从给出的完全限定名称创建一个类。

Class cDoubleArray = Class.forName("[D");

Class cStringArray = Class.forName("[[Ljava.lang.String;");


变量cDoubleArray
被声明为一个double类型数组所对应的Class(与double[].class结果相同)。变量
cStringArray
被声明为一个String类型的二维数组所对应的Class(与String[][].class结果相同)。

基本类型的包装类的TYPE字段

.class语法使用起来更方便并更适合于获取基本类型的Class;但是依然有别的方法获取。每一种基本类型以及void类型都有一个包装类用以将基本类型封装成引用类型。每一个包装类都有一个TYPE字段,字段值便是被包装的基本类型的Class。

Class c = Double.TYPE;


Double.TYPE与double.class是相同的。

Class c = Void.TYPE;


Void.TYPE与void.class是相同的。

返回Class的方法

有一些反射API可以返回Class,但这些方法只能用在Class已经被直接或间接的获取到时。


Class.getSuperclass()
返回给定类的父类。

Class c = javax.swing.JButton.class.getSuperclass();


javax.swing.JButton的父类是lavax.swing.AbstractButton。


Class.getClasses()
返回该类及其所有子类的所有的公共类、接口和枚举类型

Class<?>[] c = Character.class.getClasses();


Character有两个成员类Character.Subset和Character.UnicodeBlock。


Class.getDeclaredClasses()
返回该类所有声明的接口和枚举类型

Class<?>[] c = Character.class.getDeclaredClasses();


Character有两个公共成员类Character.Subset和Character.UnicodeBlock以及一个私有类 Character.CharacterCache。


Class.getDeclaringClass()

java.lang.reflect.Field.getDeclaringClass()

java.lang.reflect.Method.getDeclaringClass()

java.lang.reflect.Constructor.getDeclaringClass()
返回有这些成员声明的Class。匿名类将不会有声明类,但会有封闭类。

import java.lang.reflect.Field;

Field f = System.class.getField("out");
Class c = f.getDeclaringClass();


字段out在类System中声明。

public class MyClass {
static Object o = new Object() {
public void m() {}
};
static Class<c> = o.getClass().getEnclosingClass();
}


由o定义的匿名类的声明类是null。



Class.getEnclosingClass()
返回该类的立即封闭类( immediately enclosing class)

Class c = Thread.State.class().getEnclosingClass();


枚举类型Thread.State的封闭类是Thread。

public class MyClass {
static Object o = new Object() {
public void m() {}
};
static Class<c> = o.getClass().getEnclosingClass();
}


由o定义的匿名类被MyClass封闭。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: