奇怪的Java题:为什么1000 == 1000返回为False,而100 == 100会返回为True?

如果你运行如下代码:


1

2

3

4

Integer a = 1000, b = 1000

System.out.println(a == b);//1

Integer c = 100, d = 100

System.out.println(c == d);//2

你会得到以下运行结果:


1

2

false

true

我们知道,如果两个引用指向同一个对象,那么==就成立;反之,如果两个引用指向的不是同一个对象,那么==就不成立,即便两个引用的内容是一样的。因此,结果就会出现false。

这是非常有趣的地方。如果你查看Integer.java类,你会找到IntegerCache.java这个内部私有类,它为-128到127之间的所有整数对象提供缓存。

这个东西为那些数值比较小的整数提供内部缓存,当进行如此声明时:


1

Integer c = 100;

它的内部就是这样的:


1

Integer i = Integer.valueOf(100);

如果我们观察valueOf()类函数,我们可以看到


1

2

3

4

5

public static Integer valueOf(int i) {

      if (i >= IntegerCache.low && i

          return IntegerCache.cache[i + (-IntegerCache.low)];

      return new Integer(i);

    }

如果值在-128到127之间,它就会返回该缓存的实例。

因此。。。


1

Integer c = 100, d = 100;

两者指向同样的对象。

这就是为什么这段代码的结果为true了:


1

System.out.println(c == d);

现在你可能会问,为什么会为-128到127之间的所有整数设置缓存?

这是因为在这个范围内的小数值整数在日常生活中的使用频率要比其它的大得多,多次使用相同的底层对象这一特性可以通过该设置进行有效的内存优化。你可以使用reflection API任意使用这个功能。

运行下面的这段代码,你就会明白它的神奇所在了。


1

2

3

4

5

6

7

8

9

10

11

12

13

public static void main(String[] args) throws NoSuchFieldException, IllegalAccessException {

 

      Class cache = Integer.class.getDeclaredClasses()[0]; //1

      Field myCache = cache.getDeclaredField("cache"); //2

      myCache.setAccessible(true);//3

 

      Integer[] newCache = (Integer[]) myCache.get(cache); //4

      newCache[132] = newCache[133]; //5

 

      int a = 2;

      int b = a + a;

      System.out.printf("%d + %d = %d", a, a, b); //

    }

时间: 2024-10-26 21:57:40

奇怪的Java题:为什么1000 == 1000返回为False,而100 == 100会返回为True?的相关文章

【Todo】Java学习笔记 100==100 & Reflection API & Optional类详解 & DIP、IoC、DI & token/cookie/session管理会话方式

为什么1000 == 1000返回为False,而100 == 100会返回为True?   Link Java Reflection API:Link Java8 Optional 类深度解析: Link 深入理解DIP.DI及IoC容器: Link 3种会话管理的方式: Link

[转载] 在java中为什么变量1000 = 1000 返回false,但是100=100返回true?

ps:题目的意思是指定义相同内容的不同变量之间的==比较.如果直接比较(1000 == 1000)的结果是true. 运行以下代码: Integer a = 1000, b = 1000; System.out.println(a == b); Integer c = 100, d = 100; System.out.println(c == d); 结果是: false true 我们知道,如果两个引用指向不同的对象,即使对象拥有相同的内容时,他们用==比较的结果就是不相等(返回false).

为什么Java中1000==1000为false而100==100为true?

为什么Java中1000==1000为false而100==100为true? 这是一个挺有意思的讨论话题. 如果你运行下面的代码: 基本知识:我们知道,如果两个引用指向同一个对象,用==表示它们是相等的.如果两个引用指向不同的对象,用==表示它们是不相等的,即使它们的内容相同. 因此,后面一条语句也应该是false . 这就是它有趣的地方了.如果你看去看 Integer.Java 类,你会发现有一个内部私有类,IntegerCache.java,它缓存了从-128到127之间的所有的整数对象.

Java学习-013-文本文件读取实例源代码(两种数据返回格式)

此文源码主要为应用 Java 读取文本文件内容实例的源代码.若有不足之处,敬请大神指正,不胜感激! 1.读取的文本文件内容以一维数组[LinkedList<String>]的形式返回,源代码如下所示: 1 /** 2 * @function 文本文件操作:读取数据 3 * 4 * @author Aaron.ffp 5 * @version V1.0.0: autoUISelenium main.java.aaron.java.tools FileUtils.java txtRead, 201

每天一道Java题[3]

问题 为什么在重写equals()方法的同时,必须重写hashCode()方法? 解答 在<每天一道Java题[2]>中,已经对hashCode()能否判断两个对象是否相等做出了解释.equals()方法与hashCode()方法的关系如下: 如果两个对象的hashCode()返回值不一样,则equals()返回的结果必为false. 如果两个对象的hashCode()返回值一样的时候,equals()返回的结果未知. 如果两个对象的equals()返回的结果为true,则两个对象的hashC

每天一道Java题[11]

题目 synchronized怎么实现线程同步?请修改<每天一道Java题[10]>中的MyRunnableThread类以解决三个线程都获取到10的问题. 解答 方法一: 采用synchronized关键字包裹需要保证线程安全的代码块,来实现线程同步.语法格式为: Synchronized(expression){ //需同步的代码 } <每天一道Java题[10]>中的MyRunnableThread类修改为: package me.huangzijian; public cl

java笔记--用ThreadLocal管理线程,Callable&lt;V&gt;接口实现有返回值的线程

用ThreadLocal管理线程,Callable<V>接口实现有返回值的线程 ThreadLocal在我的笔记"关于线程同步"的第5种方式里面有介绍,这里就不多说了. --如果朋友您想转载本文章请注明转载地址"http://www.cnblogs.com/XHJT/p/3899890.html  "谢谢-- Callable<V>接口类似于Runnable,两者都是为了哪些其实例可能被另一个线程执行的类设计的, 但是Runnable不会返回

《深入Java虚拟机学习笔记》- 第19章 方法的调用与返回

<深入Java虚拟机学习笔记>- 第19章 方法的调用与返回

有一片1000*1000的草地,小易初始站在(1,1)(最左上角的位置)。小易在每一秒会横向或者纵向移动到相邻的草地上吃草(小易不会走出边界)。大反派超超想去捕捉可爱的小易,他手里有n个陷阱。第i个陷阱被安置在横坐标为xi ,纵坐标为yi 的位置上,小易一旦走入一个陷阱,将会被超超捕捉。你为了去解救小易,需要知道小易最少多少秒可能会走入一个陷阱,从而提前解救小易。 输入描述: 第一行为一个整数n

有一片1000*1000的草地,小易初始站在(1,1)(最左上角的位置).小易在每一秒会横向或者纵向移动到相邻的草地上吃草(小易不会走出边界).大反派超超想去捕捉可爱的小易,他手里有n个陷阱.第i个陷阱被安置在横坐标为xi ,纵坐标为yi 的位置上,小易一旦走入一个陷阱,将会被超超捕捉.你为了去解救小易,需要知道小易最少多少秒可能会走入一个陷阱,从而提前解救小易. 输入描述: 第一行为一个整数n(n ≤ 1000),表示超超一共拥有n个陷阱. 第二行有n个整数xi,表示第i个陷阱的横坐标 第三行