關於類的加載機制和反射機制只看這一篇就夠了,分析的非常詳細

類加載機制的原理

1.啟動JVM2.將需要運行的class文件加載到虛擬機內存中3.找到主類,開始執行主函數

加載步驟:

1.先委託父類加載類,如果父類已經加載,就不需要再次加載,如果父類沒有加載,再由本加載器加載2.解析類路徑,將類路徑轉換成文件路徑3.通過文件輸入流來讀取class文件,得到字節數組4.將字節數組轉換成類對象,對象的類型是Class類型

有哪些類加載器

類加載器:ClassLoaderAppClassLoader: 應用類加載器,負責加載核心類,加載自己寫的類ExtClassLoader: 擴展類加載器,負責加載擴展類庫bootstrap: JVM內置的加載器Bootstrap類加載器是JVM的一部分,是由C++編寫的,隨著啟動虛擬機就會創建一個bootstrap類加載器對象

獲得Class對象的幾種方式

1.通過類名.class

<code>Class c1 = Student.class;
/<code>

2.通過對象的getClass()方法

<code>Class c2 = stu.getClass();
/<code>

3.通過類加載器獲得class對象

<code>ClassLoader classLoader = ClassLoader.getSystemClassLoader();
Class c3 = classLoader.loadClass("com.newer.test.Student");
/<code>

4.通過 Class.forName()獲得Class對象;

<code>Class c4 =  Class.forName("com.newer.test.Student");
/<code>

總代碼:先創建學生類

<code>package com.newer.test;

public class Student {
    private int num;
    private String name;
    private int age;
    public Student(){
    }
    private Student(int num){
        this.num = num;
    }
    public Student(int num,String name,int age){
        this.num = num;
        this.name = name;
        this.age = age;
    }
    public int getNum() {
        return num;
    }
    public void setNum(int num) {
        this.num = num;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public int getAge() {
        return age;
    }
    public void setAge(int age) {
        this.age = age;
    }
    @Override
    public String toString() {
        return "Student{" +
                "num=" + num +
                ", name='" + name + '\'' +
                ", age=" + age +
                '}';
    }
}
/<code>
<code>package com.newer.test;

public class MainClass {
    public static void main(String[] args) throws  Exception{

        Student stu = new Student();

        //獲得Student的Class對象

        //1.通過類名.class
        Class c1 = Student.class;

        //2.通過對象的getClass()方法
        Class c2 = stu.getClass();

        //3.通過類加載器獲得class對象
        ClassLoader classLoader = ClassLoader.getSystemClassLoader();
        Class c3 = classLoader.loadClass("com.newer.test.Student");

        //4.通過 Class.forName()獲得Class對象;
        Class c4 = Class.forName("com.newer.test.Student");
/<code>

如何通過Class對象獲得構造方法對象

類的所有的信息都在Class對象中Class類是反射機制中的核心類

Class c = Class.forName(包名.類名);

<code>//加載類,獲得類的Class對象
Class c = Class.forName("com.newer.test.Student");
/<code>

1.獲得所有可見的構造方法

<code>//1.獲得所有可見的構造方法
Constructor[] cons= c.getConstructors();
/<code>
<code>//2.獲得所有已經聲明的構造方法
Constructor[] cons2= c.getDeclaredConstructors();
/<code>

3.獲得指定的可見的某一個構造方法

<code>//3.獲得指定的可見的某一個構造方法
Constructor cc = c.getConstructor(int.class,String.class,int.class);
/<code>

4.從聲明的方法中獲得指定的構造方法

<code>//4.從聲明的方法中獲得指定的構造方法
Constructor cc2 = c.getDeclaredConstructor(int.class);
/<code>

總代碼:學生類

<code>package com.newer.test;

public class Student {
    private int num;
    private String name;
    private int age;
    public Student(){
    }
    private Student(int num){
        this.num = num;
    }
    public Student(int num,String name,int age){
        this.num = num;
        this.name = name;
        this.age = age;
    }
    public int getNum() {
        return num;
    }
    public void setNum(int num) {
        this.num = num;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public int getAge() {
        return age;
    }
    public void setAge(int age) {
        this.age = age;
    }
    @Override
    public String toString() {
        return "Student{" +
                "num=" + num +
                ", name='" + name + '\'' +
                ", age=" + age +
                '}';
    }
}

/<code>
<code>package com.newer.test;

import java.lang.reflect.Constructor;
/**
 * 反射機制動態獲得類的信息
 */
public class FanShe {
    public static void main(String[] args) throws Exception{
        //加載類,獲得類的Class對象
        Class c = Class.forName("com.newer.test.Student");
        //通過Class對象獲得類的信息
        //1.獲得所有可見的構造方法
        Constructor[] cons= c.getConstructors();
        for (Constructor con:cons){
            System.out.println(con);
        }
        System.out.println("------------------------");
        //2.獲得所有已經聲明的構造方法
        Constructor[] cons2= c.getDeclaredConstructors();
        for (Constructor con:cons2){
            System.out.println(con);
        }
        System.out.println("------------------------");
        //3.獲得指定的可見的某一個構造方法
        Constructor cc = c.getConstructor(int.class,String.class,int.class);
        System.out.println(cc);
        System.out.println("------------------------");
        //4.從聲明的方法中獲得指定的構造方法
        Constructor cc2 = c.getDeclaredConstructor(int.class);
        System.out.println(cc2);
        System.out.println("------------------------");
      }
}
/<code>

如何通過構造方法對象實例化

<code>//通過構造方法對象得到類的實例對象
Object obj = cc.newInstance(123,"zhangsan",20);
/<code>

訪問私有構造方法:cc2.setAccessible(true);

<code>//通過私有構造方法實例化對象
//設置允許訪問私有構造方法
cc2.setAccessible(true);
Object obj2 =  cc2.newInstance(22);
/<code>

最後

感謝你看到這裡,看完有什麼的不懂的可以在評論區問我,覺得文章對你有幫助的話記得給我點個贊,每天都會分享java相關技術文章或行業資訊,歡迎大家關注和轉發文章!


分享到:


相關文章: