今天无意中发现一个怪事,当时没理解,后来跟网友讨论了才知道原理,是关于int值的加法算法,两段代码如下:

代码1:

    @Testpublic void test1() {int stackLength = 1;int count = 0;try {while(true){count++;stackLength += stackLength; //每次打印的值为0System.out.println("stackLength="+count+"次:: "+stackLength);}} catch (Exception e) {System.out.println("occur exception!!! stackLength="+stackLength);}}

控制台输出结果很奇怪,全都是0,:

stackLength=21719次:: 0
stackLength=21720次:: 0
stackLength=21721次:: 0
stackLength=21722次:: 0
stackLength=21723次:: 0
stackLength=21724次:: 0
stackLength=21725次:: 0

……  由于打印太快,已经计算了2万多次。

代码2:

    @Testpublic void test2() {int stackLength = 1;int count = 0;try {while(true){count++;stackLength += 1;System.out.println("stackLength="+count+"次:: "+stackLength);}} catch (Exception e) {System.out.println("occur exception!!! stackLength="+stackLength);}}

控制台打印结果正常,是一个数一个数加上去的:

stackLength=21211次:: 21212
stackLength=21212次:: 21213
stackLength=21213次:: 21214
stackLength=21214次:: 21215
stackLength=21215次:: 21216
stackLength=21216次:: 21217
stackLength=21217次:: 21218
stackLength=21218次:: 21219
stackLength=21219次:: 21220
stackLength=21220次:: 21221
stackLength=21221次:: 21222
stackLength=21222次:: 21223

……

思路

这就很奇怪了,代码1和代码2中,只有一行代码不一样,

在代码1中为stackLength += stackLength;

在代码2中为stackLength += 1;

但是运行2万多次后,结果却大相径庭。后来与网友讨论才明白其中原理如下:

先说  i+=i 吧,二进制运算的知识。
初始值1  就是 0000 0000 0000 0000 0000 0000 0000 0001 ,
加自己就是  0000 0000 0000 0000 0000 0000 0000 0010.
0000 0000 0000 0000 0000 0000 0000 0010 + 0000 0000 0000 0000 0000 0000 0000 0010 就=2+2  
结果就是 0000 0000 0000 0000 0000 0000 0000 0100 也就是4
一直到31次的时候,

就变成  1000 0000 0000 0000 0000 0000 0000 0000 

这个值是最小负数

因为 int是32位。当最高符号位超出32位,最后两个最大的负数相加的时候,符号位也变成0了,后32位都是0,就是32个0,所以后面就一直是0了。
当是33位时,两个最大负数相加,连33位都变成了0
因为int只能取32位
所以就是0
然后后面就一直是0+0了
好了,明白了这个道理,我们来看看是不是这样的,首先把源码改成如下:
例子3:
    @Testpublic void test3() {int stackLength = 1;int count = 0;try {while(true){count++;stackLength += stackLength;System.out.println("stackLength="+count+"次:: "+stackLength);if(count > 40){break;}}} catch (Exception e) {System.out.println("occur exception!!! stackLength="+stackLength);}}

控制台打印如预期之中:

stackLength=1次:: 2
stackLength=2次:: 4
stackLength=3次:: 8
stackLength=4次:: 16
stackLength=5次:: 32
stackLength=6次:: 64
stackLength=7次:: 128
stackLength=8次:: 256
stackLength=9次:: 512
stackLength=10次:: 1024
stackLength=11次:: 2048
stackLength=12次:: 4096
stackLength=13次:: 8192
stackLength=14次:: 16384
stackLength=15次:: 32768
stackLength=16次:: 65536
stackLength=17次:: 131072
stackLength=18次:: 262144
stackLength=19次:: 524288
stackLength=20次:: 1048576
stackLength=21次:: 2097152
stackLength=22次:: 4194304
stackLength=23次:: 8388608
stackLength=24次:: 16777216
stackLength=25次:: 33554432
stackLength=26次:: 67108864
stackLength=27次:: 134217728
stackLength=28次:: 268435456
stackLength=29次:: 536870912
stackLength=30次:: 1073741824
stackLength=31次:: -2147483648
stackLength=32次:: 0
stackLength=33次:: 0
stackLength=34次:: 0
stackLength=35次:: 0
stackLength=36次:: 0
stackLength=37次:: 0
stackLength=38次:: 0
stackLength=39次:: 0
stackLength=40次:: 0
stackLength=41次:: 0

转载于:https://www.cnblogs.com/zhuwenjoyce/p/6537928.html

java中int算法的有趣现象相关推荐

  1. java int stack_java中int算法的有趣现象

    今天无意中发现一个怪事,当时没理解,后来跟网友讨论了才知道原理,是关于int值的加法算法,两段代码如下: 代码1: @Testpublic voidtest1() {int stackLength = ...

  2. [转载] Java中为什么要有重载现象

    参考链接: 重载Java中的main() Java中为什么要有重载现象. 一句话告诉你们"节约词汇". 我们先从生活中的例子来看. 打?你会想到什么.要看宾语是什么. 打球 打孩子 ...

  3. java中int取值范围是怎么计算的?

    首先jdk中定义int占4个字节 ===> 32位(后面全部的计算都是以此为根据的) 32位就是jvm仅仅给分配32个格子的空间,用以存放数据. 总所周知计算机中用0和1存放数据. 那么,32个 ...

  4. Java 中Int转String的三种方法

    JAVA 中int类型转String类型的三种通常方法: 1.String.valueOf(int i) 2.Integer.toString(int i) 3.i + ""; / ...

  5. JAVA中int、String的类型转换(亲测)

    int -> String int i=12345; String s=""; 第一种方法:s=i+""; 第二种方法:s=String.valueOf( ...

  6. java中int转成String位数不足前面补零

    转载自:http://ych0108.iteye.com/blog/2174134 java中int转String位数不够前面补零 String.format("%010d", 2 ...

  7. Java中int和Integer的区别

    int 是基本类型,直接存数值 integer是对象,用一个引用指向这个对象 1.Java 中的数据类型分为基本数据类型和复杂数据类型 int 是前者>>integer 是后者(也就是一个 ...

  8. Java|Java中int的取值范围是多少

    Java 中 int 的取值范围是:-2^31 ~ 2^31-1 大致想一下,int 占 4字节,也就是 32 位,int 是有符号的,最高位为符号位.所以剩下31个位置. 那么我们大胆猜测一下,最大 ...

  9. Java中int的取值范围

    先上代码,通过下面代码的执行结果观察 public class Test {public static void main(String[] args) {// 2的31次方int j = (int) ...

  10. Java中int的取值范围的原因

    为什么Java中int型数据取值范围是[-231, 231-1] 为什么Java中int型数据取值范围是[-231,231-1],网上很多解释都存在问题. int是Java中的8种基本类型之一,一个i ...

最新文章

  1. 变电站越级跳闸的几大原因(转载)
  2. 授予数据库账号dba权限_数据库用户和权限
  3. Silverlight 4 Beta正式发布
  4. iPhone屏幕各种尺寸分辨率(更新至XS)
  5. 阿里云插件新版发布,多特性助力提升开发者体验
  6. 稀疏数组与二维数组相互转化
  7. centos daemonize_手把手教你在centos上配置Django项目(超详细步骤)
  8. 具有相同模式的字符串,使用正则表达式组的提取和替换的案例
  9. 富文本编辑器KindEditor在前端JS的应用
  10. 人脸对齐(十一)--PIFA2015
  11. HCIE-Security Day11:双机热备,从VRRP到VGMP
  12. HTML网页设计:七、表格
  13. SpringCLoud+redis+es高并发项目《九》(Spring Security Oauth2 JWT)
  14. Python 批处理文件(全)
  15. 什么是SAAS平台?三分钟了解
  16. OpenCV提取图像中的垂直线(或者水平线)
  17. MYSQL关闭安全模式
  18. Python爱因斯坦阶梯问题
  19. 小程序自定义导航栏搜索和自定义底部tab(动态切换)
  20. PS学习笔记----------利用图层蒙版来实现无损抠图

热门文章

  1. 石头高墙怎么放_朱良志:古人对石头的审美
  2. 享元模式在 Java String 中的应用
  3. Hive查看执行计划
  4. Spark 理论简答
  5. 解决Tomcat闪退
  6. python3.6爬淘宝信息
  7. 21套非常棒的网页设计图标素材
  8. 如果在文档已完成加载后执行 document.write,整个 HTML 页面将被覆盖
  9. Android apk如何加固防止被破解(防止逆向编译)
  10. 【JAVA源码分析——Java.lang】String源码分析