< prev index next >

src/java.base/share/classes/java/math/BigDecimal.java

Print this page




 329      */
 330     public static final BigDecimal ZERO =
 331         ZERO_THROUGH_TEN[0];
 332 
 333     /**
 334      * The value 1, with a scale of 0.
 335      *
 336      * @since  1.5
 337      */
 338     public static final BigDecimal ONE =
 339         ZERO_THROUGH_TEN[1];
 340 
 341     /**
 342      * The value 10, with a scale of 0.
 343      *
 344      * @since  1.5
 345      */
 346     public static final BigDecimal TEN =
 347         ZERO_THROUGH_TEN[10];
 348 





 349     // Constructors
 350 
 351     /**
 352      * Trusted package private constructor.
 353      * Trusted simply means if val is INFLATED, intVal could not be null and
 354      * if intVal is null, val could not be INFLATED.
 355      */
 356     BigDecimal(BigInteger intVal, long val, int scale, int prec) {
 357         this.scale = scale;
 358         this.precision = prec;
 359         this.intCompact = val;
 360         this.intVal = intVal;
 361     }
 362 
 363     /**
 364      * Translates a character array representation of a
 365      * {@code BigDecimal} into a {@code BigDecimal}, accepting the
 366      * same sequence of characters as the {@link #BigDecimal(String)}
 367      * constructor, while allowing a sub-array to be specified.
 368      *


1976      *         initial element and the remainder is the final element.
1977      * @throws ArithmeticException if {@code divisor==0}
1978      * @throws ArithmeticException if the result is inexact but the
1979      *         rounding mode is {@code UNNECESSARY}, or {@code mc.precision}
1980      *         {@literal >} 0 and the result of {@code this.divideToIntgralValue(divisor)} would
1981      *         require a precision of more than {@code mc.precision} digits.
1982      * @see    #divideToIntegralValue(java.math.BigDecimal, java.math.MathContext)
1983      * @see    #remainder(java.math.BigDecimal, java.math.MathContext)
1984      * @since  1.5
1985      */
1986     public BigDecimal[] divideAndRemainder(BigDecimal divisor, MathContext mc) {
1987         if (mc.precision == 0)
1988             return divideAndRemainder(divisor);
1989 
1990         BigDecimal[] result = new BigDecimal[2];
1991         BigDecimal lhs = this;
1992 
1993         result[0] = lhs.divideToIntegralValue(divisor, mc);
1994         result[1] = lhs.subtract(result[0].multiply(divisor));
1995         return result;





























































































































































































































1996     }
1997 
1998     /**
1999      * Returns a {@code BigDecimal} whose value is
2000      * <code>(this<sup>n</sup>)</code>, The power is computed exactly, to
2001      * unlimited precision.
2002      *
2003      * <p>The parameter {@code n} must be in the range 0 through
2004      * 999999999, inclusive.  {@code ZERO.pow(0)} returns {@link
2005      * #ONE}.
2006      *
2007      * Note that future releases may expand the allowable exponent
2008      * range of this method.
2009      *
2010      * @param  n power to raise this {@code BigDecimal} to.
2011      * @return <code>this<sup>n</sup></code>
2012      * @throws ArithmeticException if {@code n} is out of range.
2013      * @since  1.5
2014      */
2015     public BigDecimal pow(int n) {




 329      */
 330     public static final BigDecimal ZERO =
 331         ZERO_THROUGH_TEN[0];
 332 
 333     /**
 334      * The value 1, with a scale of 0.
 335      *
 336      * @since  1.5
 337      */
 338     public static final BigDecimal ONE =
 339         ZERO_THROUGH_TEN[1];
 340 
 341     /**
 342      * The value 10, with a scale of 0.
 343      *
 344      * @since  1.5
 345      */
 346     public static final BigDecimal TEN =
 347         ZERO_THROUGH_TEN[10];
 348 
 349     /**
 350      * The value 0.5, with a scale of 1.
 351      */
 352     private static final BigDecimal ONE_HALF = valueOf(5L, 1);
 353 
 354     // Constructors
 355 
 356     /**
 357      * Trusted package private constructor.
 358      * Trusted simply means if val is INFLATED, intVal could not be null and
 359      * if intVal is null, val could not be INFLATED.
 360      */
 361     BigDecimal(BigInteger intVal, long val, int scale, int prec) {
 362         this.scale = scale;
 363         this.precision = prec;
 364         this.intCompact = val;
 365         this.intVal = intVal;
 366     }
 367 
 368     /**
 369      * Translates a character array representation of a
 370      * {@code BigDecimal} into a {@code BigDecimal}, accepting the
 371      * same sequence of characters as the {@link #BigDecimal(String)}
 372      * constructor, while allowing a sub-array to be specified.
 373      *


1981      *         initial element and the remainder is the final element.
1982      * @throws ArithmeticException if {@code divisor==0}
1983      * @throws ArithmeticException if the result is inexact but the
1984      *         rounding mode is {@code UNNECESSARY}, or {@code mc.precision}
1985      *         {@literal >} 0 and the result of {@code this.divideToIntgralValue(divisor)} would
1986      *         require a precision of more than {@code mc.precision} digits.
1987      * @see    #divideToIntegralValue(java.math.BigDecimal, java.math.MathContext)
1988      * @see    #remainder(java.math.BigDecimal, java.math.MathContext)
1989      * @since  1.5
1990      */
1991     public BigDecimal[] divideAndRemainder(BigDecimal divisor, MathContext mc) {
1992         if (mc.precision == 0)
1993             return divideAndRemainder(divisor);
1994 
1995         BigDecimal[] result = new BigDecimal[2];
1996         BigDecimal lhs = this;
1997 
1998         result[0] = lhs.divideToIntegralValue(divisor, mc);
1999         result[1] = lhs.subtract(result[0].multiply(divisor));
2000         return result;
2001     }
2002 
2003 
2004     /**
2005      * Returns an approximation to the square root of {@code this}
2006      * with rounding according to the context settings.
2007      *
2008      * <p>The preferred scale of the returned result is equal to
2009      * {@code floor(this.scale()/2.0)}. The value of the returned
2010      * result is always within one ulp of the exact decimal value for
2011      * the precision in question.  If the rounding mode is {@link
2012      * RoundingMode#HALF_UP HALF_UP}, {@link RoundingMode#HALF_DOWN
2013      * HALF_DOWN}, or {@link RoundingMode#HALF_EVEN HALF_EVEN}, the
2014      * result is within one half an ulp of the exact decimal value.
2015      *
2016      * <p>Special case:
2017      * <ul>
2018      * <li> The square root of a number numerically equal to {@code
2019      * ZERO} is equal to {@code ZERO}.
2020      * </ul>
2021      *
2022      * @param mc the context to use.
2023      * @return the square root of {@code this}.
2024      * @throws ArithmeticException if {@code this} is less than zero.
2025      * @throws ArithmeticException if an exact result is requested
2026      * ({@code mc.getPrecision()==0}) and there is no finite decimal
2027      * expansion of the exact result
2028      * @throws ArithmeticException if
2029      * {@code (mc.getRoundingMode()==RoundingMode.UNNECESSARY}) and
2030      * the exact result cannot fit in {@code mc.getPrecision()}
2031      * digits.
2032      * @since  9
2033      */
2034     public BigDecimal sqrt(MathContext mc) {
2035         int signum = signum();
2036         if (signum == 1) {
2037             /*
2038              * The following code draws on the algorithm presented in
2039              * "Properly Rounded Variable Precision Square Root," Hull and
2040              * Abrham, ACM Transactions on Mathematical Software, Vol 11,
2041              * No. 3, September 1985, Pages 229-237.
2042              *
2043              * The BigDecimal computational model differs from the one
2044              * presented in the paper in several ways: first BigDecimal
2045              * numbers aren't necessarily normalized, second many more
2046              * rounding modes are supported, including UNNECESSARY, and
2047              * exact results can be requested.
2048              *
2049              * The main steps of the algorithm below are as follow, first
2050              * argument reduce the value to the numerical range [1, 10)
2051              * using the following relations:
2052              *
2053              * x = y * 10 ^ exp
2054              * sqrt(x) = sqrt(y) * 10^(exp / 2) if exp is even
2055              * sqrt(x) = sqrt(y/10) * 10 ^((exp+1)/2) is exp is odd
2056              *
2057              * Then use Newton's iteration on the reduced value to compute
2058              * the numerical digits of the desired result.
2059              *
2060              * Finally, scale back to the desired exponent range and
2061              * perform any adjustment to get the preferred scale in the
2062              * representation.
2063              */
2064 
2065             // The code below favors relative simplicity over checking
2066             // for special cases that could run faster.
2067 
2068             BigDecimal zeroWithFinalPreferredScale = valueOf(0L, this.scale()/2);
2069 
2070             // First phase of numerical normalization, strip trailing
2071             // zeros and check for even powers of 10.
2072             BigDecimal stripped = this.stripTrailingZeros();
2073             int strippedScale = stripped.scale();
2074 
2075             // Numerically, sqrt(10^2N) = 10^N
2076             if (BigInteger.ONE.equals(stripped.unscaledValue()) &&
2077                 strippedScale % 2 == 0) {
2078                 BigDecimal result = valueOf(1L, strippedScale/2);
2079                 // Adjust to requested precision and preferred scale as possible
2080                 // TODO: since max(addend.scale(), augend.scale()) only add if scale appropriate
2081                 // Result only has one precision digit as using any precision in mc is okay
2082                 return result.add(zeroWithFinalPreferredScale, mc);
2083             }
2084 
2085             System.out.println("\tStarting: " + this + "\tscale: " + this.scale()); // DEBUG
2086             System.out.println("\tStripped: " + stripped + "\tscale: " + stripped.scale()); // DEBUG
2087 
2088 
2089             // After stripTrailingZeros, the representation is normalized as
2090             //
2091             // unscaledValue * 10^(-scale)
2092             //
2093             // where unscaledValue is an integer with the mimimum
2094             // precision for the cohort of the numerical value. To
2095             // allow binary floating-point hardware to be used to get
2096             // approximately a 15 digit approximation to the square
2097             // root, it is helpful to instead normalize this as so
2098             // that the significand portion is to right of the decimal
2099             // point, roughly:
2100             //
2101             // (unscaledValue * (10^-precision) * 10^(-scale)) * (10^precision)
2102             //
2103             // so that
2104             //
2105             // sqrt(unscaledValue * (10^-precision) * 10^(-scale) * (10^precision)) =
2106             //
2107             // sqrt(unscaledValue * (10^-precision) * 10^(-scale)) * 10^(precision/2)
2108             //
2109             // Therefore, this adjustment occurs for by 10^-precision is precision is even or 
2110             // (adjust as needed, +/-1
2111             //
2112             // (A double value might have as much many as 17 decimal
2113             // digits of precision; it depends on the relative density
2114             // of binary and decimal numbers at different regions of
2115             // the number line.)
2116 
2117             // Now the precision / scale adjustment
2118             int scaleAdjust = 0;
2119             int scale = stripped.scale() - stripped.precision() + 1;
2120             if (scale % 2 == 0) {
2121                 scaleAdjust = scale;
2122             } else {
2123                 scaleAdjust = scale - 1;
2124                 // stripped = stripped.multiply(TEN); why not??
2125             }
2126 
2127             // At least document potential exponent overflow issues here???
2128             BigDecimal working = stripped.scaleByPowerOfTen(scaleAdjust);
2129             System.out.println("\tWorking2: " + working + "\tscale: " + working.scale() +
2130                                "\tadjust: " + scaleAdjust); // DEBUG
2131 
2132             // Verify 1 <= working < 10 (verify range)
2133             assert working.compareTo(ONE) >= 0 && working.compareTo(TEN) < 0;
2134 
2135             // Use good ole' Math.sqrt to get the initial guess for the
2136             // Newton iteration, good to at least 15 decimal digits.
2137             BigDecimal guess = new BigDecimal(Math.sqrt(working.doubleValue()));
2138             int guessPrecision = 15;
2139             int originalPrecision = mc.getPrecision();
2140             int targetPrecision;
2141             // If an exact value is requested, it must only need about
2142             // half of the input digits to represent since multiplying
2143             // two N digit numbers yield a 2N-1 or 2N digit result.
2144             if (originalPrecision == 0) {
2145                 targetPrecision = stripped.precision()/2 + 1;
2146             } else {
2147                 targetPrecision = originalPrecision;
2148             }
2149 
2150             // When setting the precision to use inside the Newton
2151             // iteration loop, take care to avoid the case where the
2152             // precision of the input exceeds the requested precision
2153             // and rounding the input value too soon.
2154             BigDecimal approx = guess;
2155             int workingPrecision = working.precision();
2156             do {
2157                 // If did more work, could we make sure the
2158                 // approximation was uniformly above / below the root?
2159 
2160                 System.out.println(approx); // DEBUG
2161                 int tmpPrecision = Math.max(Math.max(guessPrecision, targetPrecision + 2),
2162                                            workingPrecision);
2163                 MathContext mcTmp = new MathContext(tmpPrecision, RoundingMode.HALF_EVEN);
2164                 // approx = 0.5 * (approx + fraction / approx)
2165                 approx = ONE_HALF.multiply(approx.add(working.divide(approx, mcTmp), mcTmp));
2166                 guessPrecision *= 2;
2167             } while (guessPrecision < targetPrecision + 2);
2168 
2169             // Need additinal checking for HALF_EVEN since we are only
2170             // using two extra precision digits?
2171             BigDecimal result;
2172             RoundingMode targetRm = mc.getRoundingMode();
2173             if (targetRm == RoundingMode.UNNECESSARY || originalPrecision == 0) {
2174                 RoundingMode tmpRm =
2175                     (targetRm == RoundingMode.UNNECESSARY) ? RoundingMode.DOWN : targetRm;
2176                 MathContext mcTmp = new MathContext(targetPrecision, tmpRm);
2177                 result = approx.round(mcTmp);
2178                 result.scaleByPowerOfTen(-scaleAdjust/2);
2179                 // If result*result != the starting value numerically,
2180                 // the square root isn't exact
2181                 if (this.subtract(result.multiply(result)).compareTo(ZERO) != 0) {
2182                     throw new ArithmeticException("Computed square root not exact.");
2183                 }
2184             } else {
2185                 result = approx.round(mc);
2186                 result = result.scaleByPowerOfTen(-scaleAdjust/2);
2187             }
2188 
2189             // For now, skip the rounding up / down fix up
2190 
2191             // Read through "What every ..." for 2p + 2 discussion...
2192 
2193             // Handle 1/2 ulp, 1 ulp, and unnecessary rounding separately?
2194             // UP, DOWN,
2195             // CEILING (equiv to UP), FLOOR (equiv to DOWN), 
2196             //
2197             // HALF_UP, HALF_DOWN, HALF_EVEN -- look up 2p + 2 derivation
2198             // -- same for decimal as well as binary?
2199 
2200             // Could use direct definition to test adjacent values to
2201             // target precision -- need to lookup if Newton's iteration
2202             // converges from above or below to avoid checking three values...
2203 
2204             // Add a zero with the preferred scale with a rounding
2205             // precision equal to the original precision.
2206             
2207             // TODO: since max(addend.scale(), augend.scale()) only add if scale appropriate
2208             return result.add(zeroWithFinalPreferredScale,
2209                               new MathContext(originalPrecision, RoundingMode.UNNECESSARY));
2210         } else {
2211             switch (signum) {
2212             case -1:
2213                 throw new ArithmeticException("Attempted square root " + 
2214                                               "of negative BigDecimal");
2215             case 0:
2216                 return valueOf(0L, scale()/2);
2217 
2218             default:
2219                 throw new AssertionError("Bad value from signum");
2220             }
2221         }
2222     }
2223 
2224     /**
2225      * Returns a {@code BigDecimal} whose value is
2226      * <code>(this<sup>n</sup>)</code>, The power is computed exactly, to
2227      * unlimited precision.
2228      *
2229      * <p>The parameter {@code n} must be in the range 0 through
2230      * 999999999, inclusive.  {@code ZERO.pow(0)} returns {@link
2231      * #ONE}.
2232      *
2233      * Note that future releases may expand the allowable exponent
2234      * range of this method.
2235      *
2236      * @param  n power to raise this {@code BigDecimal} to.
2237      * @return <code>this<sup>n</sup></code>
2238      * @throws ArithmeticException if {@code n} is out of range.
2239      * @since  1.5
2240      */
2241     public BigDecimal pow(int n) {


< prev index next >