您好,我想知道声明 int[] 向量和声明 Integer[] 向量有什么区别。在课堂练习中,它已以两种方式声明,我不知道确切的区别是什么。
JLS说:
4.2. 原始类型和值
原始类型由 Java 编程语言预定义并由保留字(第 3.9 节)命名:(...)原始值不与其他原始值共享状态。数值类型是整数类型和浮点类型。
整数类型有 byte、short、int 和 long,其值分别为 8 位、16 位、32 位和 64 位二进制补码整数,(...)(第 3.1 节)。
整数Javadoc说:
Integer 类将原始类型 int 包装在一个对象中。Integer 类型的对象包含一个值为 int 类型的字段。
JLS 说的数组:
第 10 章 数组
在 Java 编程语言中,数组是对象(第 4.3.1 节),是动态创建的,并且可以分配给 Object 类型的变量(第 4.3.2 节)。Object 类的所有方法都可以在数组上调用。
一个数组对象包含许多变量。变量的数量可以为零,在这种情况下,它被称为空数组。数组中包含的变量没有名称;相反,它们被使用非负整数作为索引值的数组访问表达式引用。这些变量称为数组的组件。如果一个数组有 n 个分量,我们说 n 是数组的长度;使用从 0 到 n-1(含)的整数索引来引用数组组件。
但这并没有让我清楚 int[] 和 Integer[] 之间的区别
本质区别在于,在 JAVA 中,
int
它是原始类型,而不是对象,而它Integer
是对象或类。通俗地说:a
int
是一个数字,aInteger
是一个指针,指向一个包含整数的类。或者...更通俗地说:aInteger
是一个盒子,aint
是盒子里面的东西。这是什么意思?
在计算范围 -2,147,483,648 [-2 31 ] 和 +2,147,483,647 [2 31 -1]范围内的数字时, A
int
的速度要快得多。换句话说,a有 32 位信息可供我们直接使用。见规格。Integer.MIN_VALUE
Integer.MAX_VALUE
int
变量
int
是可变的。除非标记为final
,否则它们可以随时更改其值。一个典型的例子,int
用于在循环等中改变计数器的for
值while
。A
Integer
, 是一个包含单个字段的对象int
。AInteger
比 a 大得多int
。对象Integer
是不可变的。如果要影响变量的值Integer
,唯一的方法是创建一个新对象Integer
并丢弃旧对象。A.原语
int
int 类型的变量存储它们所代表的整数的实际二进制值。
因此,以下代码在 Java 中是错误的:
因为
int
它没有方法,所以只能声明为存储一个值。B.班级
Integer
Integer
正如我所说,它是一个类,就像任何其他 Java 类一样,具有它的方法。此代码在 Java 中是正确的:
parseInt
这是对类的静态方法的调用Integer
,它返回 aint
,而不是 aInteger
。我们可以说它
Integer
是一个只有一个 type 字段的类int
。此类用于需要int
像对待任何其他对象一样对待 a 的情况,例如在泛型类型或需要空值的情况下。什么时候应该使用其中一种?
这是一个带有一些指标的小表格:
编辑:自动装箱和拆箱
不是所有闪闪发光的都是金子,小心!
由于@LuiggiMendoza 在评论中对上表的指示提出了质疑,因此我想添加此部分,因为它可以传播有关使用自动装箱和拆箱的错误概念
从 Java 1.5 开始,允许将原语转换为对象(包装器),反之亦然。这称为自动装箱和拆箱。
以下大部分内容取自Java 文档:
A. 自动装箱
自动装箱是 Java 编译器在原始类型与其对应的对象容器类之间进行的自动转换。例如,将 a 转换
int
为 aInteger
,将 a 转换为double
aDuoble
,等等。如果转换以另一种方式完成,则称为拆箱。Java 编译器在原始值是以下情况时应用自动装箱:
这是最简单的自动装箱示例:
本节中的其余示例使用泛型...
让我们考虑以下代码:
虽然
li
值是int
作为原始类型添加的,而不是 Integer 对象,但代码是经过编译的。因为li
它是对象列表Integer
,而不是值列表int
。有人可能想知道为什么 Java 编译器不会在编译时抛出错误。编译器不会生成错误,因为它会创建一个对象并将该对象添加Integer
到i
li
. 因此,编译器在运行时将上述代码转换为以下代码:有些人认为自动装箱 - 拆箱是一种神奇的东西,很棒的东西。就个人而言,我认为不是。这里值得一问,为什么要将程序员可以做的事情委托给编译器呢?小心,因为我们可以有一个漂亮的代码,读起来很愉快,但它随时可能有一个严重的错误。
这已经足够了,但是……最重要的是,不恰当地使用自动装箱-拆箱会对小型操作产生轻微的性能损失,但可能是在不考虑操作的情况下执行程序时出错的结果必须处理大量数据或在内存容量低的设备上。
除其他外, Java 文档中明确说明了这一点:
B.拆箱
将对象从容器类型 (
Integer
) 转换为其对应的原始值 (int
) 称为拆箱。Java 编译器在包装类的对象是以下情况时应用拆箱:
让我们考虑以下方法:
由于 (%) 和 (+ =) 运算符不适用于对象
Integer
,人们可能想知道为什么 Java 编译器编译该方法而不会引发错误。编译器不会引发错误,因为它调用 intValue 方法在运行时将 a 转换Integer
为 aint
:根据 Java,这是美学问题,而不是性能问题:
这就是为什么 Java 说:
(*) 阻抗故障(阻抗不匹配)。为了理解这个概念,我将举一个例子:如果我们期望从数据库的列中获取值,该列允许为空,并且我们将该值分配给该类型的变量,
int
我们将面临一种情况,impedance mismatch
因为int
它没有承认空值,程序可能会给出错误,或者最多它会分配值0
而不是NULL
. 反之亦然,如果我们将值从 Java 发送到 DB,如果我们在 DB 中使用int
for INSERT 或 UPDATE,我们可能会将值发送到某些列而不是NULL
value0
。这可能看起来很愚蠢,在某些情况下可能是非常严重的事情。如果我们必须进行比较,我们就不要说什么。我们可能会得到意想不到的结果,因为自动装箱-拆箱掩盖了真实值,因为 a 永远不会
Integer
替代 aint
。一个是盒子,另一个是盒子里面的东西。如果我们混淆了这两件事,我们可能会犯非常严重的错误。让 Java 做应该做的事不好,还有很多原因。但这样就太牵强了...
值得注意的是,在 Java 中,每个原始类型都有一个等效的包装类:
byte
有byte
short
有Short
int
有Integer
long
有Long
boolean
有Boolean
char
有Char
float
有Float
double
有Double
首先,您必须区分什么是原始类型和对象。
对象包含属性和方法。这些属性可以是对象或原始类型。
一个对象可以赋值为null,例如:
Integer numero = null;
原始类型既不包含属性也不包含方法,并且表示最小的表达单元。
您不能将 null 分配给原始类型,例如:(编译错误)
int numero = null;
对于您的情况, int 是原始类型,而 Integer 是表示它的对象。