为什么Collat​​z猜想程序不适用于Java中的大整数

时间:2012-08-12 05:51:42

标签: java math integer-overflow collatz

这是我用来模拟Java上的Collat​​z猜想的程序:

import java.util.*;
public class Collatz {
public static void main(String args[]){
    Scanner raj= new Scanner(System.in);
    int n;
    int k=0;
    System.out.print("n? ");
    n = raj.nextInt();
    while(n > 1){
        if(n%2 ==1){
            n=3*n+1;
            System.out.println(n);
            k++;
        }
        if(n%2==0){
            n=n/2;
            System.out.println(n);
            k++;
        }

    }
    System.out.print("It took " + k + " iterations!");
}

}

当我输入n = 6时,我得到了

  

3      10      五       16       8       4       2       1       它花了8次迭代!

但是当我说,n = 63728127时,我得到了

  

191184382   95592191   286776574   143388287   430164862   215082431   645247294   322623647   967870942   483935471   1451806414   725903207   -2117257674   -1058628837   它花了14次迭代!

出了什么问题?为什么?我该如何解决?谢谢!

1 个答案:

答案 0 :(得分:4)

这是整数溢出的经典案例。原始int在Java中的范围有限。如果必须处理大整数,解决方案是始终使用BigInteger之类的东西。

顺便说一句,如果Java支持运算符重载,就像几乎所有其他现代语言一样,事情会变得容易得多。

import java.util.*;
import java.math.BigInteger;


public class Collatz {
    public static void main(String args[]){
        Scanner raj= new Scanner(System.in);
        int k=0;
        System.out.print("n? ");

        BigInteger n = BigInteger.valueOf(raj.nextLong());

        while(n.compareTo(BigInteger.ONE) > 0){
            if(n.testBit(0)){
                n = n.multiply(BigInteger.valueOf(3));
                n = n.add(BigInteger.ONE);
                System.out.println(n);
                k++;
            }
            else {
                n = n.divide(BigInteger.valueOf(2));
                System.out.println(n);
                k++;
            }
        }
        System.out.print("It took " + k + " iterations!");
    }
}