java高精度、大数演算まとめ


転載元:http://blog.himdd.com/同じ比較的いいブログです。オススメです。
************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************ではではではでは、*********************Javaは、2つのクラスBigIntegerとBigDecimalを提供しています。特に高精度演算を行うために用いられます。*演算子を使用するのではなく、BigIntegerとBigDecimalでもいいです。高精度の整数BigInteger*BigIntegerは、任意の精度の整数をサポートします。つまり、任意の大きさの整数値を精確に表します。同時に演算中には何の情報も失われません。*高精度浮動小数点数BigDecimal*は任意の精度の小数を表し、それらを計算します。*BigDecimalオブジェクトは可変ではないので、これらの方法の各々は新しいBigDecimalオブジェクトを生成します。*したがって、オブジェクトのオーバーヘッドを作成するために、BigDecimalは大量の数学的計算には適しませんが、小数点以下を正確に表示するために設計されています。******************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************//
import java.math.BigDecimal;
import java.math.BigInteger;
public class BigNumber {
//        ,         
private static final int DEFAULT_DIV_SCALE = 10;
//        
private BigNumber() {
}
/**
*          。
* @param v1    
* @param v2   
* @return       
*/
public static double add(double v1, double v2) {
   BigDecimal b1 = new BigDecimal(Double.toString(v1));
   BigDecimal b2 = new BigDecimal(Double.toString(v2));
   return (b1.add(b2)).doubleValue();
}
/**
*          。
* @param v1    
* @param v2   
* @return       
*/
public static double sub(double v1, double v2) {
   BigDecimal b1 = new BigDecimal(Double.toString(v1));
   BigDecimal b2 = new BigDecimal(Double.toString(v2));
   return (b1.subtract(b2)).doubleValue();
}
/**
*          。
* @param v1    
* @param v2   
* @return       
*/
public static double mul(double v1, double v2) {
   BigDecimal b1 = new BigDecimal(Double.toString(v1));
   BigDecimal b2 = new BigDecimal(Double.toString(v2));
   return (b1.multiply(b2)).doubleValue();
}
/**
*   (  )       ,          ,   
*         ,         。
* @param v1    
* @param v2   
* @return       
*/
public static double div(double v1, double v2) {
   return div(v1, v2, DEFAULT_DIV_SCALE);
}
/**
*   (  )       。          , scale   
*    ,         。
* @param v1    
* @param v2   
* @param scale               。
* @return       
*/
public static double div(double v1, double v2, int scale) {
   if (scale < 0) {
    System.err.println("        0!");
    return 0;
   }
   BigDecimal b1 = new BigDecimal(Double.toString(v1));
   BigDecimal b2 = new BigDecimal(Double.toString(v2));
   return (b1.divide(b2, scale, BigDecimal.ROUND_HALF_UP)).doubleValue();
}
/**
*   Factorial  !
* @param n         0 int
* @return     n!  
*/
public static BigInteger getFactorial(int n) {
   if (n < 0) {
    System.err.println("n      0!");
    return new BigInteger("-1");
   } else if (n == 0) {
    return new BigInteger("0");
   }
   //           BigInteger
   BigInteger result = new BigInteger("1");
   for (; n > 0; n--) {
    //   n       ,     BigInteger  ,        
    result = result.multiply(new BigInteger(new Integer(n).toString()));
   }
   return result;
}
public static void main(String[] args) {
   //                      ?
   System.out.println(0.05 + 0.01);
   System.out.println(1.0 - 0.42);
   System.out.println(4.015 * 100);
   System.out.println(123.3 / 100);
   //   0.060000000000000005
   //   0.5800000000000001
   //   401.49999999999994
   //   1.2329999999999999
   //    ,   n    
   int n = 30;
   System.out.println("  n   " + n + "! = " + BigNumber.getFactorial(n));
   // double  BigDecimal
   BigDecimal bd1 = new BigDecimal(0.1);
   System.out.println("(bd1 = new BigDecimal(0.1)) = " + bd1.toString());
   // String  BigDecimal
   BigDecimal bd2 = new BigDecimal("0.1");
   System.out.println("(bd2 = new BigDecimal(\"0.1\")) = "
     + bd2.toString());
   BigDecimal bd3 = new BigDecimal("0.10");
   //equals      BigDecimal      ,    true,    false
   System.out.println("bd2.equals(bd3) = " + bd2.equals(bd3));//false
   //compareTo      BigDecimal     ,    0,    -1,    1。
   System.out.println("bd2.compareTo(bd3) = " + bd2.compareTo(bd3));//0
   //      
   System.out.println("0.05 + 0.01 = " + BigNumber.add(0.05, 0.01));
   System.out.println("1.0 - 0.42 = " + BigNumber.add(1.0, 0.42));
   System.out.println("4.015 * 100 =" + BigNumber.add(4.015, 100));
   System.out.println("123.3 / 100 = " + BigNumber.add(123.3, 100));
   }
}
*************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************(1)BigIntegerとBigDecimalは可変ではありません。各ステップの演算を行う時、新しいオブジェクトが発生します。作成対象によるオーバーヘッドが発生します。*大量の数学計算には適していないので、できるだけlong、float、doubleなどの基本的なタイプを使って科学計算または工程計算を行うべきです。*BigIntegerとBigDecimalを設計する目的は、大きな整数と小数を正確に表示するために、商業計算に使用されます。*(2)BigDecimalには4つの製造方法があり、そのうちの二つはBig Integerで構成され、もう一つはdoubleで構成され、もう一つはString構造を使用している。*double構造BigDecimalを使用することは避けなければなりません。doubleでは正確に表現できない数字があります。BigDecimal構造に送る時にはもう不正確です。*例えば、new BigDecimal(0.1)によって得られた値は、0.11億555111531 1237827021181340541015625である。new BigDecimal(“0.1”)を使用して得られた値は0.1です。したがって、正確な計算が必要ならば、StringでBigDecimalを構築し、doubleで構成しないようにします。見た目は簡単ですが、*(3)equals()方法は0.1と0.1が等しいとみなして、trueに戻ります。0.10と0.1は違って、結果false_pacompreals(Tolse)に戻ります。0.1と0.1は等しいと考えられ、0.10と0.1も等しいので、2つのBigDecimal値を数値的に比較する場合はequals()*(4)ではなくcompreTo()を使うべきです。また、任意の精度の小数点以下演算はまだ正確な結果を表していない場合もあります。例えば、1を割ると9で無限ループの小数点が発生します。111111...。このため、除法演算を行う際には、BigDecimalで切り身を明示的にコントロールすることができます。*******************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************
運転結果:0.0600000 000005 0.800000 1 401.499999994 1.23299999999 n計算nの階乗30!=265298129191058636380800000(bd 1=new BigDecimal(0.1)=0.100万00000555151515151515151787878780202454545454545565(bd 2=Bidnel=Biqu)=0 0.05+0.01=0.06 1.0–0.42=1.42 4.015*100=104.15 123.3/100=223.3