2010-12-15 86 views
56
Class

的Java文档说:作为类加载由Java虚拟机自动构造什么是Class对象(java.lang.Class)?

Class对象,并通过调用的类加载器的defineClass方法。

什么是这些Class对象?它们是否与通过调用new从类中实例化的对象相同?

另外,例如object.getClass().getName()即使我不从java.lang.Class继承,如何将所有内容都转换为超类Class

回答

71

没有什么可以指定为Class。 Java中的每个Object都属于某个class。这就是为什么Object类,它由所有其他类继承,定义getClass()方法。

getClass(),或类字面 - Foo.class返回一个Class对象,其中包含关于类的一些元数据:

  • 名称
  • 方法
  • 字段
  • 构造
  • 注释

和一些有用的方法,如铸造和各种检查(isAbstract()isPrimitive()等)。 the javadoc显示您可以获得关于课程的信息。

因此,举例来说,如果你的方法给出的对象,要在案件来处理它,它的注解与@Processable批注,则:

public void process(Object obj) { 
    if (obj.getClass().isAnnotationPresent(Processable.class)) { 
     // process somehow; 
    } 
} 

在这个例子中,你获得关于给定对象的类的元数据(不管它是什么),并检查它是否有给定的注释。许多在Class实例的方法被称为“反射操作”,或简称为“反射。Read here约反思,为什么在使用时和。

还要注意,枚举和接口也代表了Class对象,并有。相应元数据

总结 - 在java中每个对象(属于)一类,和具有各自的Class对象,其中包含有关它的元数据,即在运行时访问

+26

对此进一步思考很有趣。 'Class'类继承自'Object'本身。 'Class.class'返回一个表示'Class'类的'Class'对象。你可以反思思考。我的头脑ASPLODE。 – cdhowie 2010-12-15 18:15:41

+0

@cdhowie有没有用Ruby很多,呵? :-) – 2010-12-15 18:23:44

+1

@pst:我有。这让我想伤害人。任何使用[this many](http://ruby-doc.org/core/classes/Object.html)方法的根类型的语言/框架值得埋葬。它具有PHP风格的粘性 - 随机 - 废话 - API-without-any-forethought综合征。提示火焰... – cdhowie 2010-12-15 18:26:17

7

getClass()是一种方法,其。 返回作为java.lang.Class的实例......没有涉及的演员。 Casting看起来像这样:

Class<?> type = (Class<?>) object; 
34

Class对象是一种描述对象类的元对象。它主要用于Java的反射功能。你可以把它看作是实际课堂的“蓝图”。例如。你有一个类汽车是这样的:

public class Car { 
    public String brand; 
} 

然后,你可以构造一个描述你的“汽车”类的Class对象。现在

Class myCarClass = Class.forName("Car"); 

你可以做各种各样的那类对象上你的车类查询的:

myCarClass.getName() - returns "Car" 
myCarClass.getDeclaredField("brand") - returns a Field object describing the "brand" field 

等。每个java对象都有一个方法getClass(),它返回描述Java对象Class的Class对象。所以,你可以这样做:

Car myCar = new Car(); 
Class myCarClass = myCar.getClass(); 

这也适用于你不知道的对象,例如对象,您从外面得到:

public void tellMeWhatThisObjectsClassIs(Object obj) { 
    System.out.println(obj.getClass().getName()); 
} 

您可以养活这个方法任何Java对象,并将其将打印出你给它的对象的实际类。

在使用Java时,大多数时候您不需要担心Class对象。不过,他们有一些方便的用例。例如。它们允许您以编程方式实例化某个类的实例对象,该对象经常用于对象序列化和反序列化(例如,将Java对象转换为XML并返回,主要返回)。

Class myCarClass = Class.forName("Car"); 
Car myCar = myCarClass.newInstance(); // is roughly equivalent to = new Car(); 

你也可以用它来找出你的类的所有声明的字段或方法等,这在某些情况下非常有用。所以例如如果你的方法得到一个未知的对象,你需要更多地了解它,就像它插入一些接口等,Class类是你的朋友。

这么久以来,java.lang.reflect包中的Class,Field,Method等类允许您分析定义的类,方法,字段,创建它们的新实例,调用方法all各种其他的东西,他们让你在运行时动态地做到这一点。

+0

Class c1 = Car.class;这个“班级”是什么?这是每个班级都存在的公共变量吗? – 2013-04-17 02:32:51

+4

它基本上是语法糖。它是编译器评估的东西,用给定的名称加载类对象。大致等同于Class.forName(“完全限定类名称”),但是类在编译时被检查为存在,而Class.forName()在运行时执行。 – 2013-04-17 12:12:29

2

Class对象是Class(java.lang.Class)的一个实例。下面引用来自javadoc的课程应该回答你的问题

类没有公共构造函数。相反,Class对象是由Java虚拟机自动构造的,因为在加载类时以及通过调用类加载器中的defineClass方法。

4

我还想添加到ColinD的回答是的getClass将返回同一对象为相同类型的实例。这将打印真正

MyOtherClass foo = new MyOtherClass(); 
    MyOtherClass bar = new MyOtherClass(); 
    System.out.println(foo.getClass()==bar.getClass()); 

请注意,这不是等于,我使用==