国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

2023年Java核心技術(shù)面試第三篇(篇篇萬(wàn)字精講)

這篇具有很好參考價(jià)值的文章主要介紹了2023年Java核心技術(shù)面試第三篇(篇篇萬(wàn)字精講)。希望對(duì)大家有所幫助。如果存在錯(cuò)誤或未考慮完全的地方,請(qǐng)大家不吝賜教,您也可以點(diǎn)擊"舉報(bào)違法"按鈕提交疑問。

目錄

六.? Java反射機(jī)制以及動(dòng)態(tài)代理是基于什么原理

?6.1 反射機(jī)制:

6.2 反射例子:

6.3 動(dòng)態(tài)代理:

6.4 例子:

6.5 總結(jié):

6.5.1 代理模式

6.5.1.1動(dòng)態(tài)代理:

*6.5.1.2 JDK動(dòng)態(tài)代理:

*6.5.1.3 cglib動(dòng)態(tài)代理:

6.5.1.4 反射與動(dòng)態(tài)代理原理

6.5.2 應(yīng)用場(chǎng)景:

6.5.2.3 組成要素:

6.5.2.4 實(shí)現(xiàn)方式:

七. int 和 Integer 有什么區(qū)別?? Integer的值緩存范圍?

7.1? ?int:

7.2 Integer的值緩存:

7.3 考點(diǎn)分析:

7.3.1 理解自動(dòng)裝箱,拆箱

7.3.1.1 自動(dòng)裝箱實(shí)際上是一種語(yǔ)法糖。

7.3.1.2 語(yǔ)法糖解釋:

7.3.1.2.1 語(yǔ)法糖例子

7.3.1.2.1 .1自動(dòng)裝箱和拆箱:

7.3.1.2.1.2?泛型:

7.3.1.2.1.3?Lambda表達(dá)式:

7.3.2 對(duì)象的組成

7.3.2.1對(duì)象頭:

7.3.2.2對(duì)象實(shí)例:

7.3.2.3舉個(gè)繼承有父類的例子:

7.3.2.4舉個(gè)正常的例子:

7.3.2.5 tips:

7.3.2.6 小結(jié):

7.3.2.6.1 int和Integer有什么區(qū)別?

7.3.2.6.2 對(duì)象的內(nèi)存結(jié)構(gòu)是什么樣的?


六.? Java反射機(jī)制以及動(dòng)態(tài)代理是基于什么原理

?6.1 反射機(jī)制:

Java語(yǔ)言提供的一種基礎(chǔ)功能,賦予程序在運(yùn)行時(shí)自省(introspect)的能力。

通過反射我們可以直接操作類和對(duì)象:

比如獲取某個(gè)對(duì)象的類定義,獲取類聲明的屬性和方法,調(diào)用方法或者構(gòu)造對(duì)象,甚至可以運(yùn)行時(shí)修改類定義。

6.2 反射例子:

反射的示例,展示了如何獲取類的信息、創(chuàng)建對(duì)象和調(diào)用方法

通過 Class<?> clazz = MyClass.class 獲取了類 MyClass 的定義。然后使用反射獲取了類的名稱、屬性和方法,并輸出到控制臺(tái)。

接下來,我們使用反射創(chuàng)建了 MyClass 類的對(duì)象實(shí)例,并通過反射調(diào)用了 setName()setAge() 方法來設(shè)置對(duì)象的屬性值。

最后,我們通過調(diào)用對(duì)象的 toString() 方法將對(duì)象信息輸出到控制臺(tái)。

import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;

public class ReflectionExample {
    public static void main(String[] args) throws Exception {
        // 獲取類的定義
        Class<?> clazz = MyClass.class;

        // 獲取類的名稱
        String className = clazz.getName();
        System.out.println("Class Name: " + className);

        // 獲取類聲明的屬性
        Field[] fields = clazz.getDeclaredFields();
        for (Field field : fields) {
            String fieldName = field.getName();
            System.out.println("Field Name: " + fieldName);
        }

        // 獲取類聲明的方法
        Method[] methods = clazz.getDeclaredMethods();
        for (Method method : methods) {
            String methodName = method.getName();
            System.out.println("Method Name: " + methodName);
        }

        // 創(chuàng)建對(duì)象實(shí)例
        Constructor<?> constructor = clazz.getDeclaredConstructor();
        Object obj = constructor.newInstance();

        // 調(diào)用方法
        Method setNameMethod = clazz.getDeclaredMethod("setName", String.class);
        setNameMethod.invoke(obj, "John Doe");

        Method setAgeMethod = clazz.getDeclaredMethod("setAge", int.class);
        setAgeMethod.invoke(obj, 30);

        // 輸出對(duì)象信息
        System.out.println(obj.toString());
    }
}

class MyClass {
    private String name;
    private int age;

    public MyClass() {
    }

    public void setName(String name) {
        this.name = name;
    }

    public void setAge(int age) {
        this.age = age;
    }

    @Override
    public String toString() {
        return "Name: " + name + ", Age: " + age;
    }
}

?輸出

Class Name: MyClass
Field Name: name
Field Name: age
Method Name: setName
Method Name: setAge
Name: John Doe, Age: 30

展示了如何使用反射獲取類的信息、創(chuàng)建對(duì)象實(shí)例和調(diào)用方法。通過反射,我們可以在運(yùn)行時(shí)動(dòng)態(tài)地操作類和對(duì)象,靈活應(yīng)對(duì)不同的需求

6.3 動(dòng)態(tài)代理:

是一種方便運(yùn)行時(shí)動(dòng)態(tài)構(gòu)建代理,動(dòng)態(tài)處理代理方法調(diào)用的機(jī)制,很多場(chǎng)景都是利用類似機(jī)制做到的。

比如用來面向切面的編程(AOP)

6.4 例子:

創(chuàng)建一個(gè)實(shí)現(xiàn)InvocationHandler接口的類,用于處理代理方法的調(diào)用

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;

public class LogInvocationHandler implements InvocationHandler {
    private Object target; // 目標(biāo)對(duì)象

    public LogInvocationHandler(Object target) {
        this.target = target;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        // 在方法執(zhí)行前輸出日志
        System.out.println("Before invoking " + method.getName() + "()");

        // 調(diào)用目標(biāo)對(duì)象的方法
        Object result = method.invoke(target, args);

        // 在方法執(zhí)行后輸出日志
        System.out.println("After invoking " + method.getName() + "()");

        return result;
    }
}

使用Proxy類來動(dòng)態(tài)生成代理對(duì)象,并將目標(biāo)對(duì)象和LogInvocationHandler關(guān)聯(lián)起來

import java.lang.reflect.Proxy;

public class Main {
    public static void main(String[] args) {
        UserService userService = new UserServiceImpl(); // 原始的目標(biāo)對(duì)象

        // 創(chuàng)建LogInvocationHandler實(shí)例
        LogInvocationHandler handler = new LogInvocationHandler(userService);

        // 使用Proxy類動(dòng)態(tài)生成代理對(duì)象
        UserService proxy = (UserService) Proxy.newProxyInstance(
                userService.getClass().getClassLoader(),
                userService.getClass().getInterfaces(),
                handler
        );

        // 調(diào)用代理對(duì)象的方法
        proxy.addUser("Alice");
        proxy.deleteUser("Bob");
    }
}

使用了Proxy類的newProxyInstance()方法來動(dòng)態(tài)生成代理對(duì)象。

newProxyInstance()方法接受三個(gè)參數(shù):

  1. ClassLoader loader: 指定用于定義代理類的類加載器。我們可以使用目標(biāo)對(duì)象的類加載器,通過userService.getClass().getClassLoader()獲取。

  2. Class<?>[] interfaces: 指定代理類要實(shí)現(xiàn)的接口列表。我們可以通過userService.getClass().getInterfaces()獲取目標(biāo)對(duì)象實(shí)現(xiàn)的接口數(shù)組。

  3. InvocationHandler handler: 指定用于處理代理方法調(diào)用的InvocationHandler實(shí)例。在我們的例子中,我們使用了自定義的LogInvocationHandler作為處理器。

每次調(diào)用代理對(duì)象的方法時(shí),都會(huì)經(jīng)過LogInvocationHandlerinvoke()方法。在方法執(zhí)行前,會(huì)輸出相應(yīng)的日志信息(例如"Before invoking addUser()"),然后調(diào)用目標(biāo)對(duì)象的對(duì)應(yīng)方法,最后輸出方法執(zhí)行后的日志信息(例如"After invoking addUser()")。

6.5 總結(jié):

6.5.1 代理模式

通過代理靜默地解決一些業(yè)務(wù)無關(guān)的問題,比如遠(yuǎn)程、安全、事務(wù)、日志、資源關(guān)
閉......讓應(yīng)用開發(fā)者可以只關(guān)心他的業(yè)務(wù)
靜態(tài)代理:

事先寫好代理類,可以手工編寫,也可以用工具生成。缺點(diǎn)是每個(gè)業(yè)務(wù)類都要
對(duì)應(yīng)一個(gè)代理類,非常不靈活。


6.5.1.1動(dòng)態(tài)代理:

運(yùn)行時(shí)自動(dòng)生成代理對(duì)象。缺點(diǎn)是生成代理代理對(duì)象和調(diào)用代理方法都要額外
花費(fèi)時(shí)間。


*6.5.1.2 JDK動(dòng)態(tài)代理:

基于Java反射機(jī)制實(shí)現(xiàn),必須要實(shí)現(xiàn)了接口的業(yè)務(wù)類才能用這種辦法生
成代理對(duì)象。新版本也開始結(jié)合ASM機(jī)制。


*6.5.1.3 cglib動(dòng)態(tài)代理:

基于ASM機(jī)制實(shí)現(xiàn),通過生成業(yè)務(wù)類的子類作為代理類。
Java 反射機(jī)制的常見應(yīng)用:動(dòng)態(tài)代理(AOP、RPC)、提供第三方開發(fā)者擴(kuò)展能力(Servlet容
器,JDBC連接)、第三方組件創(chuàng)建對(duì)象(DI)

6.5.1.4 反射與動(dòng)態(tài)代理原理


1 關(guān)于反射
反射最大的作用之一就在于我們可以不在編譯時(shí)知道某個(gè)對(duì)象的類型,而在運(yùn)行時(shí)通過提供
完整的”包名+類名.class”得到。注意:不是在編譯時(shí),而是在運(yùn)行時(shí)。
功能:
?在運(yùn)行時(shí)能判斷任意一個(gè)對(duì)象所屬的類。
?在運(yùn)行時(shí)能構(gòu)造任意一個(gè)類的對(duì)象。
?在運(yùn)行時(shí)判斷任意一個(gè)類所具有的成員變量和方法。
?在運(yùn)行時(shí)調(diào)用任意一個(gè)對(duì)象的方法。
說大白話就是,利用Java反射機(jī)制我們可以加載一個(gè)運(yùn)行時(shí)才得知名稱的class,獲悉其構(gòu)造
方法,并生成其對(duì)象實(shí)體,能對(duì)其fields設(shè)值并喚起其methods。


6.5.2 應(yīng)用場(chǎng)景:


反射技術(shù)常用在各類通用框架開發(fā)中。因?yàn)闉榱吮WC框架的通用性,需要根據(jù)配置文件加載
不同的對(duì)象或類,并調(diào)用不同的方法,這個(gè)時(shí)候就會(huì)用到反射——運(yùn)行時(shí)動(dòng)態(tài)加載需要加載
的對(duì)象。

6.5.2.1特點(diǎn):


由于反射會(huì)額外消耗一定的系統(tǒng)資源,因此如果不需要?jiǎng)討B(tài)地創(chuàng)建一個(gè)對(duì)象,那么就不需要
用反射。另外,反射調(diào)用方法時(shí)可以忽略權(quán)限檢查,因此可能會(huì)破壞封裝性而導(dǎo)致安全問
題。
6.5.2.2 動(dòng)態(tài)代理
為其他對(duì)象提供一種代理以控制對(duì)這個(gè)對(duì)象的訪問。在某些情況下,一個(gè)對(duì)象不適合或者不
能直接引用另一個(gè)對(duì)象,而代理對(duì)象可以在兩者之間起到中介的作用(可類比房屋中介,房
東委托中介銷售房屋、簽訂合同等)。
所謂動(dòng)態(tài)代理,就是實(shí)現(xiàn)階段不用關(guān)心代理誰(shuí),而是在運(yùn)行階段才指定代理哪個(gè)一個(gè)對(duì)象
(不確定性)。如果是自己寫代理類的方式就是靜態(tài)代理(確定性)。


6.5.2.3 組成要素:

(動(dòng)態(tài))代理模式主要涉及三個(gè)要素:
其一:抽象類接口
其二:被代理類(具體實(shí)現(xiàn)抽象接口的類)
其三:動(dòng)態(tài)代理類:實(shí)際調(diào)用被代理類的方法和屬性的類


6.5.2.4 實(shí)現(xiàn)方式:


實(shí)現(xiàn)動(dòng)態(tài)代理的方式很多,比如 JDK 自身提供的動(dòng)態(tài)代理,就是主要利用了反射機(jī)制。還有
其他的實(shí)現(xiàn)方式,比如利用字節(jié)碼操作機(jī)制,類似 ASM、CGLIB(基于 ASM)、Javassist
等。
舉例,常可采用的JDK提供的動(dòng)態(tài)代理接口InvocationHandler來實(shí)現(xiàn)動(dòng)態(tài)代理類。其中invoke
方法是該接口定義必須實(shí)現(xiàn)的,它完成對(duì)真實(shí)方法的調(diào)用。通過InvocationHandler接口,所
有方法都由該Handler來進(jìn)行處理,即所有被代理的方法都由InvocationHandler接管實(shí)際的處
理任務(wù)。此外,我們??梢栽趇nvoke方法實(shí)現(xiàn)中增加自定義的邏輯實(shí)現(xiàn),實(shí)現(xiàn)對(duì)被代理類的
業(yè)務(wù)邏輯無侵入。

七. int 和 Integer 有什么區(qū)別?? Integer的值緩存范圍?

?Java雖然被稱為面向?qū)ο蟮恼Z(yǔ)言,但是原始數(shù)據(jù)類型仍然是重要的組成元素,經(jīng)常考察原始數(shù)據(jù)類型和包裝類等Java語(yǔ)言特性。

7.1? ?int:

int是我們是整型數(shù)字,是Java的8個(gè)原始數(shù)據(jù)類型(boolean,byte,short,char,int ,float,double,long)之一。

Java語(yǔ)言雖然號(hào)稱一切都是對(duì)象,但原始數(shù)據(jù)類型是例外。

Integer 是 int 對(duì)應(yīng)的包裝類,有一個(gè)int 類型的字段存儲(chǔ)數(shù)據(jù),并且提供了基本操作,如數(shù)學(xué)運(yùn)算,int和字符串之間的轉(zhuǎn)換等

Java 5 中,引入了自動(dòng)裝箱和自動(dòng)拆箱的功能(boxing/unboxing),Java根據(jù)上下文,自動(dòng)進(jìn)行轉(zhuǎn)換,簡(jiǎn)化了相關(guān)編程。

7.2 Integer的值緩存:

涉及到Java5 中另一個(gè)改進(jìn),構(gòu)建Integer對(duì)象的傳統(tǒng)方式是直接調(diào)用構(gòu)造器,直接進(jìn)行new一個(gè)對(duì)象。

根據(jù)實(shí)踐我們發(fā)現(xiàn)大部分?jǐn)?shù)據(jù)都是集中在有限的,較小的數(shù)值范圍,因此,在Java5中新增加靜態(tài)工廠方法valueOf,調(diào)用時(shí)會(huì)利用緩存機(jī)制,帶來了性能改進(jìn),默認(rèn)值是-128到127之間。

7.3 考點(diǎn)分析:

上面的回答覆蓋了,Java里面的兩個(gè)基本要素,原始數(shù)據(jù)類型,包裝類。

自然的就擴(kuò)展:自動(dòng)裝箱,自動(dòng)拆箱機(jī)制,可能會(huì)考察對(duì)封裝類的一些設(shè)計(jì)和實(shí)踐。

7.3.1 理解自動(dòng)裝箱,拆箱

7.3.1.1 自動(dòng)裝箱實(shí)際上是一種語(yǔ)法糖。

javac替我們自動(dòng)把裝箱轉(zhuǎn)換為Integer.valueOf(),把拆箱替換為Integer.intValue(),調(diào)用的是Integer.valueOf,采取緩存。

valueOf()方法中,它是Integer類的靜態(tài)方法,用于將基本類型int或字符串轉(zhuǎn)換為對(duì)應(yīng)的Integer對(duì)象。在valueOf()方法中,針對(duì)-128到127范圍內(nèi)的整數(shù)值會(huì)使用緩存,返回預(yù)先創(chuàng)建的對(duì)象,而不是每次都創(chuàng)建新的對(duì)象。

7.3.1.2 語(yǔ)法糖解釋:

可以理解為Java平臺(tái)為我們自動(dòng)進(jìn)行的一些轉(zhuǎn)換,保證不同的寫法在運(yùn)行時(shí)等價(jià),發(fā)生在編譯階段,生成的字節(jié)碼是一樣的。

7.3.1.2.1 語(yǔ)法糖例子
7.3.1.2.1 .1自動(dòng)裝箱和拆箱:

通過自動(dòng)裝箱和拆箱的語(yǔ)法糖,我們可以直接在基本類型和對(duì)應(yīng)的包裝類之間進(jìn)行轉(zhuǎn)換,無需手動(dòng)編寫繁瑣的轉(zhuǎn)換代碼。

int num = 10;
Integer integer = num; // 自動(dòng)裝箱
int result = integer; // 自動(dòng)拆箱
7.3.1.2.1.2?泛型:

Java的泛型提供了類型安全的編程方式,使代碼更加靈活和易讀。在使用泛型時(shí),編譯器會(huì)進(jìn)行類型擦除,將泛型參數(shù)替換為實(shí)際的類型。例如,我們可以聲明一個(gè)List來存儲(chǔ)指定類型的元素,在編譯時(shí)會(huì)進(jìn)行類型檢查和轉(zhuǎn)換。

泛型解釋:

定義了一個(gè)泛型類GenericClass<T>,它有一個(gè)類型參數(shù)T。這個(gè)類包含了一個(gè)成員變量value和對(duì)應(yīng)的getter和setter方法

public class GenericClass<T> {
    private T value;

    public void setValue(T value) {
        this.value = value;
    }

    public T getValue() {
        return value;
    }
}

?在使用該泛型類時(shí),我們可以傳入不同的類型參數(shù)

GenericClass<String> strObj = new GenericClass<>();
strObj.setValue("Hello");
String strValue = strObj.getValue();

GenericClass<Integer> intObj = new GenericClass<>();
intObj.setValue(10);
Integer intValue = intObj.getValue();

我們分別實(shí)例化了兩個(gè)GenericClass對(duì)象:strObjintObj。一個(gè)使用了String類型作為類型參數(shù),另一個(gè)使用了Integer類型作為類型參數(shù)。

在編譯時(shí),由于類型擦除的原因,編譯器會(huì)將T替換為實(shí)際的類型或者限定類型。在上述代碼中,泛型參數(shù)T會(huì)被擦除為Object類型。因此,編譯器會(huì)將代碼轉(zhuǎn)換成如下形式

public class GenericClass {
    private Object value;

    public void setValue(Object value) {
        this.value = value;
    }

    public Object getValue() {
        return value;
    }
}
7.3.1.2.1.3?Lambda表達(dá)式:

Lambda表達(dá)式是一種語(yǔ)法糖,它可以簡(jiǎn)化匿名函數(shù)的編寫。通過Lambda表達(dá)式,我們可以以更精煉的方式表示函數(shù)式接口的實(shí)現(xiàn)。

匿名函數(shù):

一種沒有具體名稱的函數(shù)。它可以用來表示一段可執(zhí)行的代碼塊或邏輯,但沒有像普通函數(shù)那樣被命名。匿名函數(shù)通常用于函數(shù)式編程中,以便在需要時(shí)傳遞給其他函數(shù)或方法作為參數(shù)。

?例子1:

List<Integer> numbers = Arrays.asList(5, 3, 1, 4, 2);

// 使用匿名函數(shù)進(jìn)行升序排序
Collections.sort(numbers, new Comparator<Integer>() {
    @Override
    public int compare(Integer num1, Integer num2) {
        return num1.compareTo(num2);
    }
});

// 使用Lambda表達(dá)式進(jìn)行升序排序
Collections.sort(numbers, (num1, num2) -> num1.compareTo(num2));

System.out.println(numbers); // 輸出:[1, 2, 3, 4, 5]

例子2:

int[] numbers = {1, 2, 3, 4, 5};
for (int num : numbers) {
    System.out.println(num);
}
//對(duì)比Lambda
List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.forEach(num -> System.out.println(num));

7.3.2 對(duì)象的組成

?對(duì)象由三部分組成,對(duì)象頭,對(duì)象實(shí)例,對(duì)齊填充。

7.3.2.1對(duì)象頭:

一般是十六個(gè)字節(jié),包括兩部分,

第一部分有哈希碼,鎖狀態(tài)標(biāo)志,線程持有的 鎖,偏向線程id,gc分代年齡等。

第二部分是類型指針,也就是對(duì)象指向它的類元數(shù)據(jù)指針, 可以理解,對(duì)象指向它的類。

7.3.2.2對(duì)象實(shí)例:

就是對(duì)象存儲(chǔ)的真正有效信息,也是程序中定義各種類型的字段包括父類繼承的和子 類定義的。

虛擬機(jī)對(duì)對(duì)象字段的存儲(chǔ)順序不涉及重排序的概念。重排序主要指的是編譯器或處理器對(duì)指令執(zhí)行順序進(jìn)行優(yōu)化的行為,而不是虛擬機(jī)對(duì)對(duì)象字段在內(nèi)存中的排列順序進(jìn)行優(yōu)化

第三部分對(duì)齊填充只是一個(gè)類似占位符的作用,因?yàn)閮?nèi)存的使用都會(huì)被填充為八字節(jié)的倍數(shù)。

7.3.2.3舉個(gè)繼承有父類的例子:

定義了一個(gè)Person類和一個(gè)繼承自PersonEmployee類。Person類有一個(gè)私有字段name和一個(gè)公共方法getName()用于獲取姓名。Employee類除了繼承了Person類的字段和方法外,還添加了一個(gè)私有字段employeeId和一個(gè)公共方法getEmployeeId()用于獲取員工ID。

public class Person {
    private String name;
    
    public Person(String name) {
        this.name = name;
    }
    
    public String getName() {
        return name;
    }
}

public class Employee extends Person {
    private int employeeId;
    
    public Employee(String name, int employeeId) {
        super(name);
        this.employeeId = employeeId;
    }
    
    public int getEmployeeId() {
        return employeeId;
    }
}

創(chuàng)建一個(gè)Employee對(duì)象時(shí),它在內(nèi)存中的布局如下

對(duì)象頭(Header):16字節(jié)
├── 哈希碼、鎖狀態(tài)標(biāo)志、線程持有的鎖、偏向線程ID、GC分代年齡等信息
└── 類型指針,指向Employee類的元數(shù)據(jù)

對(duì)象實(shí)例(Instance Data):
├── name字段(String類型,引用) - 繼承自Person類
└── employeeId字段(int類型) - Employee類特有的字段

對(duì)齊填充(Padding):占位符,使對(duì)象的總大小為8字節(jié)的倍數(shù)

Employee對(duì)象的實(shí)例數(shù)據(jù)部分包含了兩個(gè)字段。其中,name字段是從Person類繼承而來的,它是一個(gè)引用類型的字段,用于存儲(chǔ)姓名信息。而employeeId字段是Employee類特有的字段,它是一個(gè)整數(shù)類型的字段,用于存儲(chǔ)員工ID。

Employee對(duì)象的實(shí)例數(shù)據(jù)部分存儲(chǔ)了name字段(繼承自Person類)和employeeId字段(Employee類特有),這些字段組成了對(duì)象的真正有效信息

7.3.2.4舉個(gè)正常的例子:

定義了一個(gè)Person類,它有兩個(gè)字段:nameage。

public class Person {
    private String name;
    private int age;
    
    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }
}

創(chuàng)建Person對(duì)象時(shí),它在內(nèi)存中的布局大致如下所示:

對(duì)象頭(Header):16字節(jié)
├── 哈希碼、鎖狀態(tài)標(biāo)志、線程持有的鎖、偏向線程ID、GC分代年齡等信息
└── 類型指針,指向Person類的元數(shù)據(jù)

對(duì)象實(shí)例(Instance Data):
├── name字段(String類型,引用)
└── age字段(int類型)

對(duì)齊填充(Padding):占位符,使對(duì)象的總大小為8字節(jié)的倍數(shù)

對(duì)象頭占據(jù)了16字節(jié),并包含了對(duì)象的哈希碼、鎖狀態(tài)等信息,以及指向Person類元數(shù)據(jù)的類型指針。接下來,對(duì)象實(shí)例部分包含了nameage兩個(gè)字段,分別是一個(gè)引用類型的String和一個(gè)基本類型的int。在內(nèi)存中,這兩個(gè)字段按照定義的順序存儲(chǔ)。

需要注意的是,虛擬機(jī)對(duì)對(duì)象字段的存儲(chǔ)順序不涉及重排序的概念。重排序主要指的是編譯器或處理器對(duì)指令執(zhí)行順序進(jìn)行優(yōu)化的行為,而不是虛擬機(jī)對(duì)對(duì)象字段在內(nèi)存中的排列順序進(jìn)行優(yōu)化。因此,在這個(gè)例子中,虛擬機(jī)不會(huì)影響對(duì)象實(shí)例中字段的存儲(chǔ)順序。

7.3.2.5 tips:

除了存儲(chǔ)空間的區(qū)別外,基本數(shù)據(jù)類型是有默認(rèn)值的,而對(duì)象數(shù)據(jù)類型沒有默認(rèn)值。比如
從數(shù)據(jù)庫(kù)中查詢用戶年齡,如果用戶并沒有設(shè)置年齡信息,數(shù)據(jù)庫(kù)中代表年齡的列age =null
,那么在使用基本數(shù)據(jù)類型接收年齡值的時(shí)候就無法區(qū)分用戶是年齡為0還是未設(shè)置年齡的情
況,所以決定使用int還是Integer的時(shí)候除了考慮性能因素還要考慮業(yè)務(wù)場(chǎng)景。

7.3.2.6 小結(jié):
7.3.2.6.1 int和Integer有什么區(qū)別?


1. int:是Java的8個(gè)原始數(shù)據(jù)類型之一(boolean,byte,char,short,int,long,floa
t,double)
2. Integer:是int對(duì)應(yīng)的包裝類,是引用類型。在Java5中,引入了自動(dòng)裝箱和自動(dòng)拆箱
功能,Java可以根據(jù)上下文,自動(dòng)進(jìn)行轉(zhuǎn)化,極大的簡(jiǎn)化了相關(guān)編程。自動(dòng)裝箱/自動(dòng)拆箱發(fā)
生在編譯期,自己調(diào)用valueOf和intValue方法來使用緩存機(jī)制(默認(rèn)緩存是-128到127之
間)。注意:new 不使用緩存
3. int訪問是直接訪問數(shù)據(jù)內(nèi)存地址,Integer是通過引用找到數(shù)據(jù)內(nèi)存地址
4. 內(nèi)存空間占用:Integer大于int
5. 數(shù)據(jù)操作效率上:int大于Integer
6. 線程安全方面:int等原始數(shù)據(jù)類型需要使用并發(fā)相關(guān)手段。Integer等包裝類可以使
用類似AtomicInteger、AtomicLong等這樣的線程安全類。
7. int等原始數(shù)據(jù)類型和Java泛型不能配合使用
8. Integer和String一樣有final修飾,是不可變類型
9. Integer中定義了bytes常量,避免了因?yàn)榄h(huán)境 64位或32位不同造成的影響
實(shí)踐中,建議避免無意中的裝箱、拆箱行為


7.3.2.6.2 對(duì)象的內(nèi)存結(jié)構(gòu)是什么樣的?


在HotSpot虛擬機(jī)中,對(duì)象在內(nèi)存中存儲(chǔ)的布局都可以分為3塊區(qū)域。
1. 對(duì)象頭(Header)
包含兩部分信息:
1. Mark Word:用于存儲(chǔ)對(duì)象自身的運(yùn)行時(shí)數(shù)據(jù),如:哈希碼(HashCode),GC
分代年齡,鎖狀態(tài)標(biāo)志,線程持有的鎖,偏向線程ID,偏向時(shí)間戳等,
2. 類型指針:即對(duì)象指向它的類元數(shù)據(jù)的指針,虛擬機(jī)通過這個(gè)指針來確定這個(gè)
對(duì)象是哪個(gè)類的實(shí)例。
另外,如果對(duì)象是Java數(shù)組,那在對(duì)象頭中還必須有一塊用國(guó)語(yǔ)記錄數(shù)組長(zhǎng)度的數(shù)
據(jù)。
2. 實(shí)例數(shù)據(jù)(Instance Data):對(duì)象真正存儲(chǔ)的有效信息,也是在程序代碼中所定義的
各種類型的字段內(nèi)容。
3. 對(duì)齊填充(Padding):對(duì)齊填充并不是必然存在的,也沒有特別的含義,它僅僅起
著占位符的作用。使對(duì)象的大小必須是8字節(jié)的整數(shù)倍。文章來源地址http://www.zghlxwxcb.cn/news/detail-661771.html

到了這里,關(guān)于2023年Java核心技術(shù)面試第三篇(篇篇萬(wàn)字精講)的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點(diǎn)僅代表作者本人,不代表本站立場(chǎng)。本站僅提供信息存儲(chǔ)空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請(qǐng)注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實(shí)不符,請(qǐng)點(diǎn)擊違法舉報(bào)進(jìn)行投訴反饋,一經(jīng)查實(shí),立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費(fèi)用

相關(guān)文章

  • 2023年MySQL實(shí)戰(zhàn)核心技術(shù)第三篇

    2023年MySQL實(shí)戰(zhàn)核心技術(shù)第三篇

    目錄 六 . 事務(wù)隔離:隔離級(jí)別,事務(wù)隔離原理,MVCC等原理的講解 6.1 解釋: 6.2?隔離性與隔離級(jí)別 6.2.1 SQL 標(biāo)準(zhǔn)的事務(wù)隔離級(jí)別: 6.2.2 事務(wù)隔離級(jí)別解釋: 6.2.3 例子: 6.2.3.1 若隔離級(jí)別是“讀未提交” 6.2.3.2 若隔離級(jí)別是“讀提交” 6.2.3.3 若隔離級(jí)別是“可重復(fù)讀” 6.2.3.

    2024年02月09日
    瀏覽(20)
  • 【Spring進(jìn)階系列丨第三篇】Spring核心技術(shù)之 IoC 與 DI 實(shí)戰(zhàn)案例

    【Spring進(jìn)階系列丨第三篇】Spring核心技術(shù)之 IoC 與 DI 實(shí)戰(zhàn)案例

    在上一篇文章中,我們學(xué)習(xí)了IoC與DI的相關(guān)概念與原理,現(xiàn)在讓我們 以HelloWorld為例,編寫一個(gè)程序,讓創(chuàng)建對(duì)象的工作由Spring幫助我們創(chuàng)建。 一同感受一下Spring框架帶給我們開發(fā)的便捷性。 這種做法是以前最常用的做法,HelloWorld這個(gè)類的對(duì)象是我們程序員自己去創(chuàng)建并為屬

    2024年02月05日
    瀏覽(26)
  • 2023年MySQL核心技術(shù)面試第一篇

    目錄 前言: MySQL開篇前言補(bǔ)充含有前三點(diǎn),先認(rèn)識(shí)大概的MySQL,從下一篇開始進(jìn)入MySQL的核心技術(shù)講解。 一 . MySQL開篇前言補(bǔ)充 存儲(chǔ):一個(gè)完整的數(shù)據(jù)存儲(chǔ)過程是怎樣的? 1.1 數(shù)據(jù)存儲(chǔ)過程 ?1.1.1 創(chuàng)建MySQl 數(shù)據(jù)庫(kù) 1.1.1.1 為什么我們要先創(chuàng)建一個(gè)數(shù)據(jù)庫(kù),而不是直接創(chuàng)建數(shù)據(jù)表

    2024年02月11日
    瀏覽(20)
  • 后端面試話術(shù)集錦第三篇:spring cloud 面試話術(shù)

    后端面試話術(shù)集錦第三篇:spring cloud 面試話術(shù)

    這是后端面試集錦第三篇博文—— spring cloud 面試話術(shù)??? Spring Cloud 是一系列框架的集合,它利用 Spring Boot 的開發(fā)便利性簡(jiǎn)化了分布式系統(tǒng)的開發(fā),比如服務(wù)發(fā)現(xiàn)、服務(wù)網(wǎng)關(guān)、服務(wù)路由、鏈路追蹤等。 他的設(shè)計(jì)目的是為了簡(jiǎn)化 Spring 應(yīng)用的搭建和開發(fā)過程。 該框架遵循

    2024年02月11日
    瀏覽(25)
  • 《Java核心技術(shù)大會(huì)2023》——AIC松鼠活動(dòng)第一期

    《Java核心技術(shù)大會(huì)2023》——AIC松鼠活動(dòng)第一期

    大會(huì)簡(jiǎn)介 人工智能在22年、23年的再次爆發(fā)讓Python成為編程語(yǔ)言里最大的贏家;云原生的持續(xù)普及令Go、Rust等新生的語(yǔ)言有了進(jìn)一步叫板傳統(tǒng)技術(shù)體系的資本與底氣。我們必須承認(rèn)在近幾年里,Java陣營(yíng)的確受到了前所未有的挑戰(zhàn),出現(xiàn)了更多更強(qiáng)大的競(jìng)爭(zhēng)者。 但是,迄今Ja

    2024年02月16日
    瀏覽(24)
  • 「Java核心技術(shù)大會(huì) 2023」——小解送書第三期

    「Java核心技術(shù)大會(huì) 2023」——小解送書第三期

    目錄 共同深入探討 Java 生態(tài)!直播預(yù)約:視頻號(hào)“IT閱讀排行榜” 抽獎(jiǎng) 大會(huì)簡(jiǎn)介 人工智能在22年、23年的再次爆發(fā)讓Python成為編程語(yǔ)言里最大的贏家;云原生的持續(xù)普及令Go、Rust等新生的語(yǔ)言有了進(jìn)一步叫板傳統(tǒng)技術(shù)體系的資本與底氣。我們必須承認(rèn)在近幾年里,Java陣營(yíng)的

    2024年02月09日
    瀏覽(20)
  • Java語(yǔ)言第三篇集合

    集合和數(shù)組的對(duì)比 數(shù)組的長(zhǎng)度是不可變的,集合的長(zhǎng)度是可變的。 數(shù)組可以存基本數(shù)據(jù)類型和引用數(shù)據(jù)類型。集合只能存引用數(shù)據(jù)類型,如果要存基本數(shù)據(jù)類型,需要存對(duì)應(yīng)的包裝類。 Collection 集合 是單例集合的頂層接口,它表示一組對(duì)象,這些對(duì)象也稱為Collection的元素

    2024年01月23日
    瀏覽(19)
  • 「Java核心技術(shù)大會(huì) 2023」6月啟動(dòng),邀你共同探討Java生態(tài)

    「Java核心技術(shù)大會(huì) 2023」6月啟動(dòng),邀你共同探討Java生態(tài)

    ???♂? 個(gè)人主頁(yè):@艾派森的個(gè)人主頁(yè) ???作者簡(jiǎn)介:Python學(xué)習(xí)者 ?? 希望大家多多支持,我們一起進(jìn)步!?? 如果文章對(duì)你有幫助的話, 歡迎評(píng)論 ??點(diǎn)贊???? 收藏 ??加關(guān)注+ ????????人工智能在22年、23年的再次爆發(fā)讓Python成為編程語(yǔ)言里最大的贏家;云原生的持

    2024年02月10日
    瀏覽(34)
  • 「Java核心技術(shù)大會(huì) 2023」6月重磅啟動(dòng),邀你共同探討Java生態(tài)

    「Java核心技術(shù)大會(huì) 2023」6月重磅啟動(dòng),邀你共同探討Java生態(tài)

    前言 ??作者簡(jiǎn)介: 熱愛跑步的恒川 ,致力于C/C++、Java、Python等多編程語(yǔ)言,熱愛跑步,喜愛音樂的一位博主。 ??本文收錄于恒川的日常匯報(bào)系列,大家有興趣的可以看一看 ??相關(guān)專欄C語(yǔ)言初階、C語(yǔ)言進(jìn)階系列等,大家有興趣的可以看一看 ??Python零基礎(chǔ)入門系列,Jav

    2024年02月09日
    瀏覽(17)
  • Java零基礎(chǔ)教學(xué)文檔第三篇:JDBC

    Java零基礎(chǔ)教學(xué)文檔第三篇:JDBC

    今日新篇章 【JDBC】 【主要內(nèi)容】 JDBC概述 使用JDBC完成添加操作 使用JDBC完成更新和刪除 DBUtils的簡(jiǎn)單封裝 使用JDBC完成查詢 使用JDBC完成分頁(yè)查詢 常用接口詳解 JDBC批處理 SQL注入問題 事務(wù)處理解決轉(zhuǎn)賬問題 連接池 使用反射對(duì)DBUtils再次的封裝 BaseDAO的封裝 【學(xué)習(xí)目標(biāo)】 1.1

    2024年01月19日
    瀏覽(26)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請(qǐng)作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包