Java中的包装类(wrapper class)

1.介绍

顾名思义,包装类是封装Java原始类型的对象。每个Java原始类型都有一个对应的包装类:

基本类型 包装类
boolean Boolean
byte Byte
short Short
char Character
int Integer
long Long
float Float
double Double

这些都是在java.lang包中定义的,因此我们不需要手动导入它们。

2.包装类

那为什么要引入包装类?这个问题也是常见的面试题。

因为泛型类只处理对象,不支持原始类型。因此,如果我们想使用它们,就必须将原始类型值转换为包装类对象。例如,Java集合框架只处理对象。很久以前(在Java5之前,大约15年前)没有自动装箱,我们不能简单地对整数集合调用add(5)。

当时,这些原始类型值需要手动转换为相应的包装类并存储在集合中。

今天,通过自动装箱,我们可以很容易地执行ArrayList.add(101),但是Java在内部将原始类型值转换为整数,然后使用valueOf()方法将其存储在ArrayList中。

总结起来就是:Java是一个面相对象的编程语言,基本类型并不具有对象的性质,为了让基本类型也具有对象的特征,就出现了包装类型(如我们在使用集合类型Collection时就一定要使用包装类型而非基本类型),它相当于将基本类型“包装起来”,使得它具有了对象的性质,并且为其添加了属性和方法,丰富了基本类型的操作。

3.原始类型转换为包装类

现在问题是:我们如何将原始类型值转换成相应的包装类,例如int到Integer或char到Character?

答案是:可以使用构造函数或静态工厂方法将原始类型值转换为包装类的对象。

但是,到了Java9,许多装箱原始类型(如Integer或Long)的构造函数已经被弃用。

所以强烈建议只对新代码使用工厂方法。让我们看一个在Java中将int值转换为Integer对象的示例:

Integer object = new Integer(1);

Integer anotherObject = Integer.valueOf(1);

valueOf()方法返回一个表示指定int值的实例。

它返回缓存的值,所以更高效。其缓存-128到127之间的值,但也可以缓存此范围之外的其他值。

同样的,我们还可以将布尔值转换为布尔值、字节转换为字节、字符转换为字符、长转换为长、浮点数转换为浮点数、双精度转换为双精度。不过,如果必须将字符串转换为整数,则需要使用parseInt()方法,因为String不是包装类。

另一方面,要从包装类对象转换为原始类型值,可以使用相应的方法,如intValue()、doubleValue()等:

int val = object.intValue();

4.自动装箱和拆箱

在上一节中,我们演示了如何手动将原始类型值转换为对象。在Java5之后,这种转换可以通过使用称为自动装箱和取消装箱的特性自动完成。“装箱”是指将原始类型值转换为相应的包装器对象。因为这可以自动发生,所以称为自动装箱。类似地,当包装器对象被展开为一个原始类型值时,这被称为取消装箱。

实际上,这意味着我们可以将原始类型值传递给需要包装对象的方法,或将原始类型赋给需要对象的变量:

List<Integer> list = new ArrayList<>();
list.add(1); // autoboxing

Integer val = 2; // autoboxing

在本例中,Java将自动将原始类型int值转换为包装类对象。在内部,它使用valueOf()方法来转换。例如,以下代码是等效的:

Integer value = 3;
Integer value = Integer.valueOf(3);

虽然这使得转换更容易,代码更易读,但有些情况下我们不应该使用自动装箱,例如在循环中。

与自动装箱类似,给需要原始类型的方法传包装类对象或将其赋给原始类型变量时,会自动执行自动拆箱:

Integer object = new Integer(1); 
int val1 = getSquareValue(object); //unboxing
int val2 = object; //unboxing

public static int getSquareValue(int i) {
    
    
    return i*i;
}

基本上,如果我们编写了一个接受原始类型值或包装类对象的方法,我们仍然可以将这两个值传递给它们。Java将负责类型判断并完成自动装箱和拆箱,具体取决于上下文。

本文代码相对简单,不提供源码。

Guess you like

Origin blog.csdn.net/IndexMan/article/details/118001138