2021
11/24
0:30
你的位置:首页 > Java教程 > Class类简介

Class类简介

发布时间:2021-11-24 00:30:10

原标题:Class类简介

Class类

Java中所有的类,接口,枚举,注解,数组,基本数据类型,void关键字,都有Class对象。通过Class对象可以得到类的完整结构,一个Class对象在jvm中只有一个实例。

获取类实例测试代码

package com.kuang;public class Test { public static void main(String[] args) throws ClassNotFoundException {  Person person = new Student();  System.out.println("这个人是 " + person.name);  //方式一 通过getClass()获取类  Class c1 = person.getClass();  System.out.println(c1.hashCode());  //方式二 通过forName获取类 可以获取到静态的类  Class c2 = Class.forName("com.kuang.Student");  System.out.println(c2.hashCode());  //方式三 通过类名.class获得  Class<Student> c3 = Student.class;  System.out.println(c3.hashCode());  //方式4 基本内置类型的 `包装类` 都有一个Type属性 通过该属性获得  Class<Integer> c4 = Integer.TYPE;  System.out.println(c4);  // 获取父类的类型  Class c5 = c1.getSuperclass();  System.out.println(c5); }}class Person { public String name; public Person() {} public Person(String name) {  this.name = name; } @Override public String toString() {  return "Person{" +    "name='" + name + '\'' +    '}'; }}class Student extends Person { public Student() {  this.name = "学生"; }}class Teacher extends Person { public Teacher() {  this.name = "老师"; }}
package com.kuang;//哪些类有class对象import java.lang.annotation.ElementType;public class Test2 { public static void main(String[] args) {  Class c1 = Object.class; //类  Class c2 = Comparable.class;//接口  Class c3 = String[].class;//一维数组  Class c4 = int[][].class;//二位数据  Class c5 = Override.class;//注解  Class c6 = ElementType.class;//枚举  Class c7 = Integer.class;//基本类型的包装类  Class c8 = void.class;//void  Class c9 = Class.class;///Class  System.out.println(c1);  System.out.println(c2);  System.out.println(c3);  System.out.println(c4);  System.out.println(c5);  System.out.println(c6);  System.out.println(c7);  System.out.println(c8);  System.out.println(c9);//输出结果 注意数组的输出结果有点特殊//  class java.lang.Object//  interface java.lang.Comparable//  class [Ljava.lang.String;//  class [[I//  interface java.lang.Override//  class java.lang.annotation.ElementType//  class java.lang.Integer//  void//  class java.lang.Class }}

Class类实际是一个泛型类。

Class常用方法

JAVA内存分析

java类装载过程分为3步:

1,加载

Jvm把class文件字节码加载到内存中,并将这些静态数据装换成运行时数据区中方法区的类型数据,在运行时数据区堆中生成一个代表这个类的java.lang.Class对象,作为方法区类数据的访问入口。

注:方法区不仅仅是存放方法,它还存放的是类的类型信息(class对象)。

2,链接

执行下面的校验准备解析步骤,其中解析步骤是可选

  • 校验:检查加载的class文件的正确性和安全性

  • 准备:为类变量(static)分配存储空间并设置类变量初始值(变量类型的默认值),类变量随类型信息存放在方法区中,生命周期很长,使用不当很容易造成内存泄漏。

  • 解析:jvm将常量池内的符号引用(常量名)转换为直接引用(地址)

3,初始化

执行类变量赋值静态代码块

Class.forName和ClassLoader的区别?

在了解了类装载过程之后我们继续比较二者区别:
Classloder.loaderClass(String name)
其实该方法内部调用的是:Classloder. loadClass(name, false)
方法:Classloder. loadClass(String name, boolean resolve)
a:参数name代表类的全限定类名
b:参数resolve代表是否解析,resolve为true是解析该类

Class.forName(String name)
其实该方法内部调用的是:Class.forName(className, true, ClassLoader.getClassLoader(caller))
方法:Class.forName0(String name, boolean initialize, ClassLoader loader)

参数name代表全限定类名

参数initialize表示是否初始化该类,为true是初始化该类

参数loader 对应的类加载器

两者最大的区别

  • Class.forName除了将类的.class文件加载到jvm中之外,还会对类进行解释,执行类中的static块。也会加载静态方法。
  • classloader只干一件事情,就是将.class文件加载到jvm中,不会执行static中的内容,只有在newInstance才会去执行static块。
  • Class.forName(name,initialize,loader)带参数也可控制是否加载static块。并且只有调用了newInstance()方法才执行构造函数,创建类的对象。

测试代码

package com.kuang;public class ClassloaderAndForNameTest { public static void main(String[] args) {  String wholeNameLine = "com.kuang.Line";  String wholeNamePoint = "com.kuang.Point";  System.out.println("下面是测试Classloader的效果");  testClassloader(wholeNameLine, wholeNamePoint);  System.out.println();  System.out.println("下面是测试Class.forName的效果");  testForName(wholeNameLine, wholeNamePoint); } /**  * classloader  * @param wholeNameLine  * @param wholeNamePoint  */ private static void testClassloader(String wholeNameLine, String wholeNamePoint) {  Class<?> line;  Class<?> point;  ClassLoader loader = ClassLoader.getSystemClassLoader();  try {   line = loader.loadClass(wholeNameLine);   point = loader.loadClass(wholeNamePoint);   System.out.println("line " + line.getName());   System.out.println("point " + point.getName());  } catch (ClassNotFoundException e) {   e.printStackTrace();  } } /**  * Class.forName  * @param wholeNameLine  * @param wholeNamePoint  */ private static void testForName(String wholeNameLine, String wholeNamePoint) {  try {   Class<?> line = Class.forName(wholeNameLine);   Class<?> point = Class.forName(wholeNamePoint);   System.out.println("line " + line.getName());   System.out.println("point " + point.getName());  } catch (ClassNotFoundException e) {   e.printStackTrace();  } }}class Point { static {  System.out.println("静态代码块执行: loading point"); } public static String s = getString(); private static String getString() {  System.out.println("静态方法执行给静态变量赋值:loading point");  return "mask"; } public static void test() {  System.out.println("普通静态方法执行:loading point"); } {  System.out.println("point普通代码块"); } public Point() {  System.out.println("point构造方法执行"); }}class Line { static {  System.out.println("静态代码块执行: loading line"); } public static String s = getString(); private static String getString() {  System.out.println("给静态变量赋值的静态方法执行:loading line");  return "mask"; } public static void test() {  System.out.println("普通静态方法执行:loading line"); } {  System.out.println("普通代码块"); } public Line() {  System.out.println("构造方法执行"); }}//输出结果://下面是测试Classloader的效果//line com.kuang.Line//point com.kuang.Point////下面是测试Class.forName的效果//静态代码块执行: loading line//给静态变量赋值的静态方法执行:loading line//静态代码块执行: loading point//静态方法执行给静态变量赋值:loading point//line com.kuang.Line//point com.kuang.Point



原标题:Class类简介

关键词:Java,接口,JVM,class

转载请保留本文网址: http://www.www.d5897.com/a/1272406.html
*特别声明:以上内容来自于网络收集,著作权属原作者所有,如有侵权,请联系我们: admin#www.d5897.com (#换成@)。
Baidu