Class对象:class对象包含了与类有关的信息,每个类都有一个Class对象,每当我们编写并且编译了一个新类就会产生一个Class对象。
    Class作用:用来创建一个类的实例(对象),执行RTTI(运行时类型信息);

    Class.foName():通过该方法,获得一个类的Class对象的引用。从而可以在运行时使用类型信息。从而在对象还没有没有被new的时候去执行所有的静态域(包括静态域的初始化)。

    1. package com.package14;
    2. class Candy {
    3. static {
    4. System.out.println("gandy 糖果");
    5. }
    6. }
    7. class Gum {
    8. static {
    9. System.out.println("Gum 口香糖");
    10. }
    11. }
    12. class Cookie {
    13. static {
    14. System.out.println("cookie 曲奇");
    15. }
    16. }
    17. public class SweetShop {
    18. public static void main(String[] args) {
    19. System.out.println("inside main");
    20. new Candy();
    21. System.out.println("After creating Gandy");
    22. try {
    23. //手动去加载Gum类,从而在运行时使用该类的类型信息(加载类中的静态域)
    24. Class.forName("com.package14.Gum");
    25. } catch (ClassNotFoundException e) {
    26. System.err.println("not found Gum");
    27. }
    28. System.out.println("After Class.foName()");
    29. new Cookie();
    30. System.out.println("After creating Cookie");
    31. }
    32. }
    1. 同时,使用ClassforName或一个类的Class引用后,该引用将会被加载到内存中去,以备我们去实例化。<br /> 获取详细的类型信息:<br /> 1.获取类中的信息:
    1. interface HasBatteries { }
    2. interface Waterproof { }
    3. interface Shoots { }
    4. class Toy { Toy() { }
    5. Toy(int i) { }
    6. }
    7. class FancyToy extends Toy implements HasBatteries, Waterproof, Shoots {
    8. FancyToy() { super(1);}
    9. }
    10. public class ToyTest {
    11. static void info(Class cc) {//通过类Class 对象拿到该类的类型信息
    12. System.out.println("Class Name:" + cc.getName());
    13. System.out.println("Class is interface:" + cc.isInterface());
    14. System.out.println("Simple name:" + cc.getSimpleName());
    15. System.out.println("Canonical name" + cc.getCanonicalName());
    16. }
    17. public static void main(String[] args) {
    18. Class c = null;
    19. try {
    20. c = Class.forName("com.package14.FancyToy");
    21. } catch (ClassNotFoundException e) {
    22. System.out.println("Can't find FancyToy");
    23. System.exit(1);//参数不为0是停止虚拟机
    24. }
    25. info(c);//获得FanyToy类的类型信息

    获取类的继承体系(从下往上)
    image.png
    1.获取类实现的接口:
    ①先拿到类的Class对象②:使用getInterfaces方法

    1. package com.package14;
    2. interface HasBatteries { }
    3. interface Waterproof { }
    4. interface Shoots { }
    5. class Toy { Toy() { }
    6. Toy(int i) { }
    7. }
    8. class FancyToy extends Toy implements HasBatteries, Waterproof, Shoots {
    9. FancyToy() { super(1);}
    10. }
    11. public class ToyTest {
    12. static void info(Class cc) {//通过类Class 对象拿到该类的类型信息
    13. System.out.println("Class Name:" + cc.getName());
    14. System.out.println("Class is interface:" + cc.isInterface());
    15. System.out.println("Simple name:" + cc.getSimpleName());
    16. System.out.println("Canonical name" + cc.getCanonicalName());
    17. }
    18. public static void main(String[] args) {
    19. Class c = null;
    20. try {
    21. c = Class.forName("com.package14.FancyToy");
    22. } catch (ClassNotFoundException e) {
    23. System.out.println("Can't find FancyToy");
    24. System.exit(1);//参数不为0是停止虚拟机
    25. }
    26. info(c);//获得FanyToy类的类型信息
    27. System.out.println("该类中实现的接口有");//拿到fancyToy类中实现的接口
    28. for (Class cInterface : c.getInterfaces()) {
    29. System.out.println(cInterface);
    30. }

    2.获取超类信息(父类):
    ①:获得该类的Class对象②:使用getSuperclass方法拿到父类③:newInstance()创建父类,然后在拿取父类的信息

    1. public class ToyTest {
    2. static void info(Class cc) {//通过类Class 对象拿到该类的类型信息
    3. System.out.println("Class Name:" + cc.getName());
    4. System.out.println("Class is interface:" + cc.isInterface());
    5. System.out.println("Simple name:" + cc.getSimpleName());
    6. System.out.println("Canonical name" + cc.getCanonicalName());
    7. }
    8. public static void main(String[] args) {
    9. Class c = null;
    10. try {
    11. c = Class.forName("com.package14.FancyToy");
    12. } catch (ClassNotFoundException e) {
    13. System.out.println("Can't find FancyToy");
    14. System.exit(1);//参数不为0是停止虚拟机
    15. }
    16. Class superclass = c.getSuperclass();//获得该类的父类
    17. Object obj=null;
    18. System.out.println("父类的类信息为:");
    19. try {
    20. obj=superclass.newInstance();//创建父类
    21. } catch (InstantiationException e) {
    22. System.out.println("实例化异常");
    23. System.exit(1);
    24. } catch (IllegalAccessException e) {
    25. System.out.println("访问异常");
    26. System.exit(1);
    27. }
    28. info(obj.getClass());//拿到父类的信息
    29. }
    30. }

    使用类时的三部曲:
    加载.class的时候不会执行初始化

    1. 加载:由类加载器执行,会去查找类的字节码,并从这些字节码中创建一个Class对象
    2. 链接:验证类的字节码,并为静态域没分配空间
    3. 初始化:执行初始化,先父类的静态域、子类静态域,然后父类普通域、构造器。子类普通域、构造器

    对静态域的调用会执行静态域的初始化操作,对于常数静态域的掉用则不会。静态常数可以在高并发的时候随意使用

    1. package com.package14;
    2. class StaticDemo1{
    3. static final int SFI= 47;
    4. static{
    5. System.out.println("执行初始化11111");
    6. }
    7. }
    8. class StaticDemo2{
    9. static int SFI= 47;
    10. static{
    11. System.out.println("执行初始化11111");
    12. }
    13. }
    14. public class ClassInitallization2 {
    15. public static void main(String[] args) {
    16. System.out.println(StaticDemo1.SFI);
    17. System.out.println(StaticDemo2.SFI);
    18. }
    19. }

    泛化的class引用
    class的引用表示的就是他所指的对象的确切类型,我们也可以使用泛型,对其所指的类型进行限定。
    注意:每个类的Class对象都是不同的,所以对有继承关系的类来说,他们的Class对象之间没有继承关系

    1. package com.package14;
    2. public class GenericClasss {
    3. public static void main(String[] args) {
    4. Class<Integer> ints = int.class;
    5. Class integerClassass = int.class;
    6. //同一个对象的Class对象相等
    7. System.out.println(ints==integerClassass);
    8. //Integer虽然是Number的子类,但他们的Class对象并不能这样指定,以下代码报错
    9. //Class<Number> numberClass = Integer.class;
    10. //只能通过泛型边界符来指定
    11. Class<?extends Number> numberClass1 = Integer.class;
    12. }
    13. }
    14. /*===========================================================================*/
    15. package com.package14;
    16. class Goo{}
    17. class SubGoo extends Goo{}
    18. class SubGoo2 extends Goo{}
    19. class SubGoo3{}
    20. public class GenericClassReferences {
    21. public static void main(String[] args) {
    22. //SubGooClass 和GooClass没有继承关系
    23. Class<? extends Goo> subGooClass = SubGoo.class;//通过通配符可以指定
    24. subGooClass=SubGoo2.class;//也可以指定其他
    25. //subGooClass=SubGoo3.class;//不在一个继承体系不可以,除非通配符指向Object
    26. }
    27. }