“由于开发人员可以想出描述数字的类,他们决定像真正的开发人员一样发挥创造力。”
“首先,他们提出了一个抽象的 Number 类,从中派生了 Byte、Short、Integer、Long、Float 和 Double。它具有帮助将数字转换为其他数字类型的方法。”
Number 类的方法 | |
---|---|
1个 |
|
2个 |
|
3个 |
|
4个 |
|
5个 |
|
6个 |
|
“对。毕竟,你不能这样写:”
Long x = 100000;
Integer y = (Integer) x;
“是的,这些类型不是原始类型。这就是我们使用 Number 类方法的原因:”
Long x = 100000;
Integer y = x.intValue();
“但仍有几件事需要考虑。因为 Integer 不是 int,所以 Integer 对象无法与经典的 «==» 运算符进行比较。”
int x = 500;
int y = 500;
x == y; //true
Integer x = 500;
Integer y = 500;
x == y; //false
x.equals(y); //true
“正是。不知怎的,我没有立刻想到这一点。”
“但还有更多。”
“你在短路我的电路!还有什么?”
“当我们将 int 值分配给 Integer 变量时,将调用 Integer.valueOf 方法:”
代码 | 真正发生了什么 |
---|---|
|
|
“是啊,我已经从上面的例子中明白了。”
“但是,valueOf 函数并不总是创建一个新的 Integer 对象。”
“呃,‘不总是’是什么意思?”
“它缓存从 -128 到 127 的值。”
代码 | 真正发生了什么 | 描述 |
---|---|---|
|
|
变量 x、y 和 z 包含对不同对象的引用 |
|
|
变量 x、y 和 z 包含对同一对象的引用。 |
|
|
变量 z 和 t 包含对同一对象的引用。 |
“也就是说,情况是这样的:”
1) 如果我们写«new Integer()»,那么我们保证得到一个新对象。
2) 如果我们显式地或通过自动装箱调用 Integer.valueOf(),那么如果数字参数在 -128 到 127 的范围内,该方法可能会返回一个新对象或缓存的对象。
“从缓存中返回对象的方法有什么可怕的?”
“没关系。你只需要知道,有时,当你不期望它时,对象可能是相等的。任何具有相等性的东西都很复杂。如果我们比较一个原始的和一个非原始的,那么它们被当作原始的进行比较:”
int x = 300;
Integer y = 300;
Integer z = 300;
x == y; //true (comparison based on primitive value)
x == z; //true (comparison based on primitive value)
y == z; //false (comparison based on references)
int x = 100;
Integer y = 100;
Integer z = 100;
x == y; //true (comparison based on primitive value)
x == z; //true (comparison based on primitive value)
y == z; //true (comparison based on references; they point to the same object)
int x = 100;
Integer y = new Integer(100);
Integer z = 100;
x == y; //true (comparison based on primitive value)
x == z; //true (comparison based on primitive value)
y == z; //false (comparison based on references; they point to different objects)
“太好了……我要怎么记住这些呢?”
“你不需要记住这个。你只需要了解这一切是如何组织的,以及当原始和非原始对应物发挥作用时实际发生了什么。”
“我还建议你看看Integer类的方法,它有很多好用的方法,你甚至经常使用其中一个。”
“是的,我记得。Integer.parseInt();”
GO TO FULL VERSION