12ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller/* GENERATED SOURCE. DO NOT MODIFY. */
2f86f25d102340da66b9c7cb6b2d5ecdc0de43ecfFredrik Roubert// © 2016 and later: Unicode, Inc. and others.
3f86f25d102340da66b9c7cb6b2d5ecdc0de43ecfFredrik Roubert// License & terms of use: http://www.unicode.org/copyright.html#License
42ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller/*
52ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller *******************************************************************************
62ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * Copyright (C) 1996-2015, International Business Machines Corporation and    *
72ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * others. All Rights Reserved.                                                *
82ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller *******************************************************************************
92ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller */
102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fullerpackage android.icu.text;
112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fullerimport java.math.BigInteger;
132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller/**
152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <code>DigitList</code> handles the transcoding between numeric values and
162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * strings of characters.  It only represents non-negative numbers.  The
172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * division of labor between <code>DigitList</code> and
182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <code>DecimalFormat</code> is that <code>DigitList</code> handles the radix
192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * 10 representation issues and numeric conversion, including rounding;
202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <code>DecimalFormat</code> handles the locale-specific issues such as
212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * positive and negative representation, digit grouping, decimal point,
222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * currency, and so on.
232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller *
242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <p>A <code>DigitList</code> is a representation of a finite numeric value.
252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <code>DigitList</code> objects do not represent <code>NaN</code> or infinite
262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * values.  A <code>DigitList</code> value can be converted to a
272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <code>BigDecimal</code> without loss of precision.  Conversion to other
282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * numeric formats may involve loss of precision, depending on the specific
292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * value.
302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller *
312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <p>The <code>DigitList</code> representation consists of a string of
322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * characters, which are the digits radix 10, from '0' to '9'.  It also has a
332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * base 10 exponent associated with it.  The value represented by a
342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <code>DigitList</code> object can be computed by mulitplying the fraction
352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * <em>f</em>, where 0 <= <em>f</em> < 1, derived by placing all the digits of
362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * the list to the right of the decimal point, by 10^exponent.
372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller *
382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @see java.util.Locale
392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @see java.text.Format
402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @see NumberFormat
412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @see DecimalFormat
422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @see java.text.ChoiceFormat
432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @see java.text.MessageFormat
442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @version      1.18 08/12/98
452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * @author       Mark Davis, Alan Liu
463b84259b78fc811b14079dfde655d68a389b36dbPaul Duffin * @hide Made public for testing
472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller * */
483b84259b78fc811b14079dfde655d68a389b36dbPaul Duffinpublic final class DigitList {
492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * The maximum number of significant digits in an IEEE 754 double, that
512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * is, in a Java double.  This must not be increased, or garbage digits
522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * will be generated, and should not be decreased, or accuracy will be lost.
532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public static final int MAX_LONG_DIGITS = 19; // == Long.toString(Long.MAX_VALUE).length()
552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public static final int DBL_DIG = 17;
562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * These data members are intentionally public and can be set directly.
592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     *
602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * The value represented is given by placing the decimal point before
612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * digits[decimalAt].  If decimalAt is < 0, then leading zeros between
622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * the decimal point and the first nonzero digit are implied.  If decimalAt
632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * is > count, then trailing zeros between the digits[count-1] and the
642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * decimal point are implied.
652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     *
662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Equivalently, the represented value is given by f * 10^decimalAt.  Here
672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * f is a value 0.1 <= f < 1 arrived at by placing the digits in Digits to
682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * the right of the decimal.
692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     *
702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * DigitList is normalized, so if it is non-zero, figits[0] is non-zero.  We
712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * don't allow denormalized numbers because our exponent is effectively of
722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * unlimited magnitude.  The count value contains the number of significant
732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * digits present in digits[].
742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     *
752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Zero is represented by any DigitList with count == 0 or with each digits[i]
762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * for all i <= count == '0'.
772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public int decimalAt = 0;
792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public int count = 0;
802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public byte[] digits = new byte[MAX_LONG_DIGITS];
812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private final void ensureCapacity(int digitCapacity, int digitsToCopy) {
832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (digitCapacity > digits.length) {
842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            byte[] newDigits = new byte[digitCapacity * 2];
852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            System.arraycopy(digits, 0, newDigits, 0, digitsToCopy);
862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            digits = newDigits;
872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Return true if the represented number is zero.
922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    boolean isZero()
942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    {
952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i=0; i<count; ++i) if (digits[i] != '0') return false;
962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return true;
972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller// Unused as of ICU 2.6 - alan
1002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    /**
1012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * Clears out the digits.
1022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * Use before appending them.
1032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * Typically, you set a series of digits with append, then at the point
1042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * you hit the decimal point, you set myDigitList.decimalAt = myDigitList.count;
1052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * then go on appending digits.
1062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     */
1072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    public void clear () {
1082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        decimalAt = 0;
1092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        count = 0;
1102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    }
1112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
1132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Appends digits to the list.
1142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
1152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public void append (int digit) {
1162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        ensureCapacity(count+1, count);
1172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        digits[count++] = (byte) digit;
1182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
1192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public byte getDigitValue(int i) {
1212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return (byte) (digits[i] - '0');
1222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
1232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
1252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Utility routine to get the value of the digit list
1262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * If (count == 0) this throws a NumberFormatException, which
1272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * mimics Long.parseLong().
1282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
1292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final double getDouble() {
1302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (count == 0) return 0.0;
1312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        StringBuilder temp = new StringBuilder(count);
1322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        temp.append('.');
1332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i = 0; i < count; ++i) temp.append((char)(digits[i]));
1342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        temp.append('E');
1352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        temp.append(Integer.toString(decimalAt));
1362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return Double.valueOf(temp.toString()).doubleValue();
1372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // long value = Long.parseLong(temp.toString());
1382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // return (value * Math.pow(10, decimalAt - count));
1392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
1402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
1422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Utility routine to get the value of the digit list.
1432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * If (count == 0) this returns 0, unlike Long.parseLong().
1442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
1452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final long getLong() {
1462ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // for now, simple implementation; later, do proper IEEE native stuff
1472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1482ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (count == 0) return 0;
1492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // We have to check for this, because this is the one NEGATIVE value
1512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // we represent.  If we tried to just pass the digits off to parseLong,
1522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // we'd get a parse failure.
1532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (isLongMIN_VALUE()) return Long.MIN_VALUE;
1542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        StringBuilder temp = new StringBuilder(count);
1562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i = 0; i < decimalAt; ++i)
1572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        {
1582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            temp.append((i < count) ? (char)(digits[i]) : '0');
1592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
1602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return Long.parseLong(temp.toString());
1612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
1622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
1632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
1642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Return a <code>BigInteger</code> representing the value stored in this
1652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * <code>DigitList</code>.  This method assumes that this object contains
1662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * an integral value; if not, it will return an incorrect value.
1672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * [bnf]
1682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param isPositive determines the sign of the returned result
1692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @return the value of this object as a <code>BigInteger</code>
1702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
1712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public BigInteger getBigInteger(boolean isPositive) {
1722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (isZero()) return BigInteger.valueOf(0);
1732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        //Eclipse stated the following is "dead code"
1742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        /*if (false) {
1752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            StringBuilder stringRep = new StringBuilder(count);
1762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (!isPositive) {
1772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                stringRep.append('-');
1782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
1792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            for (int i=0; i<count; ++i) {
1802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                stringRep.append((char) digits[i]);
1812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
1822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            int d = decimalAt;
1832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            while (d-- > count) {
1842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                stringRep.append('0');
1852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
1862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return new BigInteger(stringRep.toString());
1872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        } else*/ {
1882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            int len = decimalAt > count ? decimalAt : count;
1892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (!isPositive) {
1902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                len += 1;
1912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
1922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            char[] text = new char[len];
1932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            int n = 0;
1942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (!isPositive) {
1952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                text[0] = '-';
1962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                for (int i = 0; i < count; ++i) {
1972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    text[i+1] = (char)digits[i];
1982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
1992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                n = count+1;
2002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            } else {
2012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                for (int i = 0; i < count; ++i) {
2022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    text[i] = (char)digits[i];
2032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
2042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                n = count;
2052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
2062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            for (int i = n; i < text.length; ++i) {
2072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                text[i] = '0';
2082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
2092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return new BigInteger(new String(text));
2102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
2112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
2122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
2132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private String getStringRep(boolean isPositive) {
2142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (isZero()) return "0";
2152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        StringBuilder stringRep = new StringBuilder(count+1);
2162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (!isPositive) {
2172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            stringRep.append('-');
2182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
2192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        int d = decimalAt;
2202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (d < 0) {
2212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            stringRep.append('.');
2222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            while (d < 0) {
2232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                stringRep.append('0');
2242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                ++d;
2252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
2262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            d = -1;
2272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
2282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i=0; i<count; ++i) {
2292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (d == i) {
2302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                stringRep.append('.');
2312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
2322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            stringRep.append((char) digits[i]);
2332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
2342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        while (d-- > count) {
2352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            stringRep.append('0');
2362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
2372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return stringRep.toString();
2382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
2392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
2402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
2412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Return an <code>ICU BigDecimal</code> representing the value stored in this
2422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * <code>DigitList</code>.
2432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * [bnf]
2442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param isPositive determines the sign of the returned result
2452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @return the value of this object as a <code>BigDecimal</code>
2462ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
2472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public android.icu.math.BigDecimal getBigDecimalICU(boolean isPositive) {
2482ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (isZero()) {
2492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return android.icu.math.BigDecimal.valueOf(0);
2502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
2512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // if exponential notion is negative,
2522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // we prefer to use BigDecimal constructor with scale,
2532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // because it works better when extremely small value
2542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // is used.  See #5698.
2552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        long scale = (long)count - (long)decimalAt;
2562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (scale > 0) {
2572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            int numDigits = count;
2582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (scale > (long)Integer.MAX_VALUE) {
2592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                // try to reduce the scale
2602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                long numShift = scale - (long)Integer.MAX_VALUE;
2612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                if (numShift < count) {
2622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    numDigits -= numShift;
2632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                } else {
2642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    // fallback to 0
2652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    return new android.icu.math.BigDecimal(0);
2662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
2672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
2682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            StringBuilder significantDigits = new StringBuilder(numDigits + 1);
2692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (!isPositive) {
2702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                significantDigits.append('-');
2712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
2722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            for (int i = 0; i < numDigits; i++) {
2732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                significantDigits.append((char)digits[i]);
2742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
2752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            BigInteger unscaledVal = new BigInteger(significantDigits.toString());
2762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return new android.icu.math.BigDecimal(unscaledVal, (int)scale);
2772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        } else {
2782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return new android.icu.math.BigDecimal(getStringRep(isPositive));
2792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
2802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
2812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
2822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
2832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Return whether or not this objects represented value is an integer.
2842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * [bnf]
2852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @return true if the represented value of this object is an integer
2862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
2872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    boolean isIntegral() {
2882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Trim trailing zeros.  This does not change the represented value.
2892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        while (count > 0 && digits[count - 1] == (byte)'0') --count;
2902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return count == 0 || decimalAt >= count;
2912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
2922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
2932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller// Unused as of ICU 2.6 - alan
2942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    /**
2952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * Return true if the number represented by this object can fit into
2962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * a long.
2972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     */
2982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    boolean fitsIntoLong(boolean isPositive)
2992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    {
3002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // Figure out if the result will fit in a long.  We have to
3012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // first look for nonzero digits after the decimal point;
3022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // then check the size.  If the digit count is 18 or less, then
3032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // the value can definitely be represented as a long.  If it is 19
3042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // then it may be too large.
3052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
3062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // Trim trailing zeros.  This does not change the represented value.
3072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        while (count > 0 && digits[count - 1] == (byte)'0') --count;
3082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
3092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        if (count == 0) {
3102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            // Positive zero fits into a long, but negative zero can only
3112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            // be represented as a double. - bug 4162852
3122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            return isPositive;
3132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        }
3142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
3152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        if (decimalAt < count || decimalAt > MAX_LONG_DIGITS) return false;
3162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
3172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        if (decimalAt < MAX_LONG_DIGITS) return true;
3182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
3192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // At this point we have decimalAt == count, and count == MAX_LONG_DIGITS.
3202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // The number will overflow if it is larger than 9223372036854775807
3212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // or smaller than -9223372036854775808.
3222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        for (int i=0; i<count; ++i)
3232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        {
3242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            byte dig = digits[i], max = LONG_MIN_REP[i];
3252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            if (dig > max) return false;
3262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            if (dig < max) return true;
3272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        }
3282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
3292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // At this point the first count digits match.  If decimalAt is less
3302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // than count, then the remaining digits are zero, and we return true.
3312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        if (count < decimalAt) return true;
3322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
3332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // Now we have a representation of Long.MIN_VALUE, without the leading
3342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // negative sign.  If this represents a positive value, then it does
3352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // not fit; otherwise it fits.
3362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        return !isPositive;
3372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    }
3382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
3392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller// Unused as of ICU 2.6 - alan
3402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    /**
3412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * Set the digit list to a representation of the given double value.
3422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * This method supports fixed-point notation.
3432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * @param source Value to be converted; must not be Inf, -Inf, Nan,
3442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * or a value <= 0.
3452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * @param maximumFractionDigits The most fractional digits which should
3462ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * be converted.
3472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     */
3482ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    public final void set(double source, int maximumFractionDigits)
3492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    {
3502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        set(source, maximumFractionDigits, true);
3512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    }
3522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
3532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
3542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Set the digit list to a representation of the given double value.
3552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * This method supports both fixed-point and exponential notation.
3562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param source Value to be converted; must not be Inf, -Inf, Nan,
3572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * or a value <= 0.
3582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits The most fractional or total digits which should
3592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * be converted.
3602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param fixedPoint If true, then maximumDigits is the maximum
3612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * fractional digits to be converted.  If false, total digits.
3622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
3632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    final void set(double source, int maximumDigits, boolean fixedPoint)
3642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    {
3652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (source == 0) source = 0;
3662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Generate a representation of the form DDDDD, DDDDD.DDDDD, or
3672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // DDDDDE+/-DDDDD.
3682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        String rep = Double.toString(source);
3692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
3702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        didRound = false;
3712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
3722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        set(rep, MAX_LONG_DIGITS);
3732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
3742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (fixedPoint) {
3752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // The negative of the exponent represents the number of leading
3762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // zeros between the decimal and the first non-zero digit, for
3772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // a value < 0.1 (e.g., for 0.00123, -decimalAt == 2).  If this
3782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // is more than the maximum fraction digits, then we have an underflow
3792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // for the printed representation.
3802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (-decimalAt > maximumDigits) {
3812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                count = 0;
3822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                return;
3832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            } else if (-decimalAt == maximumDigits) {
3842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                if (shouldRoundUp(0)) {
3852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    count = 1;
3862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    ++decimalAt;
3872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    digits[0] = (byte)'1';
3882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                } else {
3892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    count = 0;
3902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
3912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                return;
3922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
3932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // else fall through
3942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
3952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
3962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Eliminate trailing zeros.
3972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        while (count > 1 && digits[count - 1] == '0')
3982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            --count;
3992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
4002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Eliminate digits beyond maximum digits to be displayed.
4012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Round up if appropriate.
4022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        round(fixedPoint ? (maximumDigits + decimalAt) : maximumDigits == 0 ? -1 : maximumDigits);
4032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
4042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
4052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
4062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Given a string representation of the form DDDDD, DDDDD.DDDDD,
4072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * or DDDDDE+/-DDDDD, set this object's value to it.  Ignore
4082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * any leading '-'.
4092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
4102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private void set(String rep, int maxCount) {
4112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        decimalAt = -1;
4122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        count = 0;
4132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        int exponent = 0;
4142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Number of zeros between decimal point and first non-zero digit after
4152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // decimal point, for numbers < 1.
4162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        int leadingZerosAfterDecimal = 0;
4172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        boolean nonZeroDigitSeen = false;
4182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Skip over leading '-'
4192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        int i=0;
4202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (rep.charAt(i) == '-') {
4212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            ++i;
4222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
4232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (; i < rep.length(); ++i) {
4242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            char c = rep.charAt(i);
4252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (c == '.') {
4262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                decimalAt = count;
4272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            } else if (c == 'e' || c == 'E') {
4282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                ++i;
4292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                // Integer.parseInt doesn't handle leading '+' signs
4302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                if (rep.charAt(i) == '+') {
4312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    ++i;
4322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
4332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                exponent = Integer.valueOf(rep.substring(i)).intValue();
4342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                break;
4352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            } else if (count < maxCount) {
4362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                if (!nonZeroDigitSeen) {
4372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    nonZeroDigitSeen = (c != '0');
4382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    if (!nonZeroDigitSeen && decimalAt != -1) {
4392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        ++leadingZerosAfterDecimal;
4402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    }
4412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
4422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
4432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                if (nonZeroDigitSeen) {
4442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    ensureCapacity(count+1, count);
4452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    digits[count++] = (byte)c;
4462ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
4472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
4482ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
4492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (decimalAt == -1) {
4502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            decimalAt = count;
4512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
4522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        decimalAt += exponent - leadingZerosAfterDecimal;
4532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
4542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
4552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
4562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Return true if truncating the representation to the given number
4572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * of digits will result in an increment to the last digit.  This
4582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * method implements half-even rounding, the default rounding mode.
4592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * [bnf]
4602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits the number of digits to keep, from 0 to
4612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * <code>count-1</code>.  If 0, then all digits are rounded away, and
4622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * this method returns true if a one should be generated (e.g., formatting
4632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * 0.09 with "#.#").
4642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @return true if digit <code>maximumDigits-1</code> should be
4652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * incremented
4662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
4672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private boolean shouldRoundUp(int maximumDigits) {
4682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // variable not used boolean increment = false;
4692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Implement IEEE half-even rounding
4702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        /*Bug 4243108
4712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller          format(0.0) gives "0.1" if preceded by parse("99.99") [Richard/GCL]
4722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        */
4732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (maximumDigits < count) {
4742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (digits[maximumDigits] > '5') {
4752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                return true;
4762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            } else if (digits[maximumDigits] == '5' ) {
4772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                for (int i=maximumDigits+1; i<count; ++i) {
4782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    if (digits[i] != '0') {
4792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        return true;
4802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    }
4812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
4822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                return maximumDigits > 0 && (digits[maximumDigits-1] % 2 != 0);
4832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
4842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
4852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return false;
4862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
4872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
4882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
4892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Round the representation to the given number of digits.
4902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits The maximum number of digits to be shown.
4912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Upon return, count will be less than or equal to maximumDigits.
4922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * This now performs rounding when maximumDigits is 0, formerly it did not.
4932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
4942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final void round(int maximumDigits) {
4952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Eliminate digits beyond maximum digits to be displayed.
4962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Round up if appropriate.
4972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // [bnf] rewritten to fix 4179818
4982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (maximumDigits >= 0 && maximumDigits < count) {
4992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (shouldRoundUp(maximumDigits)) {
5002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                // Rounding up involves incrementing digits from LSD to MSD.
5012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                // In most cases this is simple, but in a worst case situation
5022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                // (9999..99) we have to adjust the decimalAt value.
5032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                for (;;)
5042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                {
5052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    --maximumDigits;
5062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    if (maximumDigits < 0)
5072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    {
5082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        // We have all 9's, so we increment to a single digit
5092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        // of one and adjust the exponent.
5102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        digits[0] = (byte) '1';
5112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        ++decimalAt;
5122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        maximumDigits = 0; // Adjust the count
5132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        didRound = true;
5142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                        break;
5152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    }
5162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
5172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    ++digits[maximumDigits];
5182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    didRound = true;
5192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    if (digits[maximumDigits] <= '9') break;
5202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                    // digits[maximumDigits] = '0'; // Unnecessary since we'll truncate this
5212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                }
5222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                ++maximumDigits; // Increment for use as count
5232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
5242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            count = maximumDigits;
5252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
5262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Bug 4217661 DecimalFormat formats 1.001 to "1.00" instead of "1"
5272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Eliminate trailing zeros. [Richard/GCL]
5282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // [dlf] moved outside if block, see ticket #6408
5292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        while (count > 1 && digits[count-1] == '0') {
5302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller          --count;
5312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
5322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
5332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
5342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    // Value to indicate that rounding was done.
5352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private boolean didRound = false;
5362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
5372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
5382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Indicates if last digit set was rounded or not.
5392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * true indicates it was rounded.
5402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * false indicates rounding has not been done.
5412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
5422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public boolean wasRounded() {
5432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return didRound;
5442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
5452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
5462ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
5472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Utility routine to set the value of the digit list from a long
5482ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
5492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final void set(long source)
5502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    {
5512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        set(source, 0);
5522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
5532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
5542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
5552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Set the digit list to a representation of the given long value.
5562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param source Value to be converted; must be >= 0 or ==
5572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Long.MIN_VALUE.
5582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits The most digits which should be converted.
5592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * If maximumDigits is lower than the number of significant digits
5602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * in source, the representation will be rounded.  Ignored if <= 0.
5612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
5622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final void set(long source, int maximumDigits)
5632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    {
5642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // This method does not expect a negative number. However,
5652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // "source" can be a Long.MIN_VALUE (-9223372036854775808),
5662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // if the number being formatted is a Long.MIN_VALUE.  In that
5672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // case, it will be formatted as -Long.MIN_VALUE, a number
5682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // which is outside the legal range of a long, but which can
5692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // be represented by DigitList.
5702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // [NEW] Faster implementation
5712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        didRound = false;
5722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
5732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (source <= 0) {
5742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (source == Long.MIN_VALUE) {
5752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                decimalAt = count = MAX_LONG_DIGITS;
5762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                System.arraycopy(LONG_MIN_REP, 0, digits, 0, count);
5772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            } else {
5782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                count = 0;
5792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                decimalAt = 0;
5802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
5812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        } else {
5822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            int left = MAX_LONG_DIGITS;
5832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            int right;
5842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            while (source > 0) {
5852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                digits[--left] = (byte) (((long) '0') + (source % 10));
5862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                source /= 10;
5872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            }
5882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            decimalAt = MAX_LONG_DIGITS-left;
5892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // Don't copy trailing zeros
5902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // we are guaranteed that there is at least one non-zero digit,
5912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            // so we don't have to check lower bounds
5922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            for (right = MAX_LONG_DIGITS - 1; digits[right] == (byte) '0'; --right) {}
5932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            count = right - left + 1;
5942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            System.arraycopy(digits, left, digits, 0, count);
5952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
5962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (maximumDigits > 0) round(maximumDigits);
5972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
5982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
5992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
6002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Set the digit list to a representation of the given BigInteger value.
6012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * [bnf]
6022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param source Value to be converted
6032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits The most digits which should be converted.
6042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * If maximumDigits is lower than the number of significant digits
6052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * in source, the representation will be rounded.  Ignored if <= 0.
6062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
6072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final void set(BigInteger source, int maximumDigits) {
6082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        String stringDigits = source.toString();
6092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        count = decimalAt = stringDigits.length();
6112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        didRound = false;
6122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Don't copy trailing zeros
6142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        while (count > 1 && stringDigits.charAt(count - 1) == '0') --count;
6152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        int offset = 0;
6172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (stringDigits.charAt(0) == '-') {
6182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            ++offset;
6192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            --count;
6202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            --decimalAt;
6212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
6222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        ensureCapacity(count, 0);
6242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i = 0; i < count; ++i) {
6252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            digits[i] = (byte) stringDigits.charAt(i + offset);
6262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
6272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (maximumDigits > 0) round(maximumDigits);
6292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
6302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
6322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Internal method that sets this digit list to represent the
6332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * given value.  The value is given as a String of the format
6342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * returned by BigDecimal.
6352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param stringDigits value to be represented with the following
6362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * syntax, expressed as a regular expression: -?\d*.?\d*
6372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Must not be an empty string.
6382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits The most digits which should be converted.
6392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * If maximumDigits is lower than the number of significant digits
6402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * in source, the representation will be rounded.  Ignored if <= 0.
6412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param fixedPoint If true, then maximumDigits is the maximum
6422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * fractional digits to be converted.  If false, total digits.
6432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
6442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private void setBigDecimalDigits(String stringDigits,
6452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                                     int maximumDigits, boolean fixedPoint) {
6462ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        // Find the first non-zero digit, the decimal, and the last non-zero digit.
6472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        int first=-1, last=stringDigits.length()-1, decimal=-1;
6482ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        for (int i=0; (first<0 || decimal<0) && i<=last; ++i) {
6492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            char c = stringDigits.charAt(i);
6502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            if (c == '.') {
6512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|                decimal = i;
6522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            } else if (first < 0 && (c >= '1' && c <= '9')) {
6532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|                first = i;
6542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            }
6552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        }
6562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|
6572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        if (first < 0) {
6582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            clear();
6592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            return;
6602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        }
6612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|
6622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        // At this point we know there is at least one non-zero digit, so the
6632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        // following loop is safe.
6642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        for (;;) {
6652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            char c = stringDigits.charAt(last);
6662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            if (c != '0' && c != '.') {
6672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|                break;
6682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            }
6692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            --last;
6702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        }
6712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|
6722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        if (decimal < 0) {
6732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            decimal = stringDigits.length();
6742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        }
6752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|
6762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        count = last - first;
6772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        if (decimal < first || decimal > last) {
6782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            ++count;
6792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        }
6802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        decimalAt = decimal - first;
6812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        if (decimalAt < 0) {
6822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            ++decimalAt;
6832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        }
6842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|
6852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        ensureCapacity(count, 0);
6862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        for (int i = 0; i < count; ++i) {
6872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            digits[i] = (byte) stringDigits.charAt(first++);
6882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            if (first == decimal) {
6892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|                ++first;
6902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|            }
6912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//|        }
6922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        didRound = false;
6942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // The maxDigits here could also be Integer.MAX_VALUE
6962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        set(stringDigits, stringDigits.length());
6972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
6982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Eliminate digits beyond maximum digits to be displayed.
6992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Round up if appropriate.
7002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    // {dlf} Some callers depend on passing '0' to round to mean 'don't round', but
7012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    // rather than pass that information explicitly, we rely on some magic with maximumDigits
7022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    // and decimalAt.  Unfortunately, this is no good, because there are cases where maximumDigits
7032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    // is zero and we do want to round, e.g. BigDecimal values -1 < x < 1.  So since round
7042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    // changed to perform rounding when the argument is 0, we now force the argument
7052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    // to -1 in the situations where it matters.
7062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        round(fixedPoint ? (maximumDigits + decimalAt) : maximumDigits == 0 ? -1 : maximumDigits);
7072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
7082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
7102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Set the digit list to a representation of the given BigDecimal value.
7112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * [bnf]
7122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param source Value to be converted
7132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits The most digits which should be converted.
7142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * If maximumDigits is lower than the number of significant digits
7152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * in source, the representation will be rounded.  Ignored if <= 0.
7162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param fixedPoint If true, then maximumDigits is the maximum
7172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * fractional digits to be converted.  If false, total digits.
7182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
7192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final void set(java.math.BigDecimal source,
7202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                          int maximumDigits, boolean fixedPoint) {
7212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        setBigDecimalDigits(source.toString(), maximumDigits, fixedPoint);
7222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
7232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /*
7252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Set the digit list to a representation of the given BigDecimal value.
7262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * [bnf]
7272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param source Value to be converted
7282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param maximumDigits The most digits which should be converted.
7292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * If maximumDigits is lower than the number of significant digits
7302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * in source, the representation will be rounded.  Ignored if <= 0.
7312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * @param fixedPoint If true, then maximumDigits is the maximum
7322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * fractional digits to be converted.  If false, total digits.
7332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
7342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public final void set(android.icu.math.BigDecimal source,
7352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                          int maximumDigits, boolean fixedPoint) {
7362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        setBigDecimalDigits(source.toString(), maximumDigits, fixedPoint);
7372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
7382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7392ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
7402ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Returns true if this DigitList represents Long.MIN_VALUE;
7412ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * false, otherwise.  This is required so that getLong() works.
7422ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
7432ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private boolean isLongMIN_VALUE()
7442ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    {
7452ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (decimalAt != count || count != MAX_LONG_DIGITS)
7462ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return false;
7472ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7482ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            for (int i = 0; i < count; ++i)
7492ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        {
7502ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (digits[i] != LONG_MIN_REP[i]) return false;
7512ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
7522ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7532ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return true;
7542ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
7552ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7562ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    private static byte[] LONG_MIN_REP;
7572ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7582ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    static
7592ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    {
7602ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        // Store the representation of LONG_MIN without the leading '-'
7612ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        String s = Long.toString(Long.MIN_VALUE);
7622ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        LONG_MIN_REP = new byte[MAX_LONG_DIGITS];
7632ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i=0; i < MAX_LONG_DIGITS; ++i)
7642ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        {
7652ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            LONG_MIN_REP[i] = (byte)s.charAt(i + 1);
7662ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        }
7672ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
7682ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7692ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller// Unused -- Alan 2003-05
7702ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    /**
7712ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * Return the floor of the log base 10 of a given double.
7722ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * This method compensates for inaccuracies which arise naturally when
7732ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * computing logs, and always give the correct value.  The parameter
7742ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     * must be positive and finite.
7752ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//     */
7762ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    private static final int log10(double d)
7772ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    {
7782ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // The reason this routine is needed is that simply taking the
7792ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // log and dividing by log10 yields a result which may be off
7802ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // by 1 due to rounding errors.  For example, the naive log10
7812ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // of 1.0e300 taken this way is 299, rather than 300.
7822ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        double log10 = Math.log(d) / LOG10;
7832ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        int ilog10 = (int)Math.floor(log10);
7842ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // Positive logs could be too small, e.g. 0.99 instead of 1.0
7852ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        if (log10 > 0 && d >= Math.pow(10, ilog10 + 1))
7862ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        {
7872ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            ++ilog10;
7882ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        }
7892ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        // Negative logs could be too big, e.g. -0.99 instead of -1.0
7902ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        else if (log10 < 0 && d < Math.pow(10, ilog10))
7912ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        {
7922ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//            --ilog10;
7932ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        }
7942ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//        return ilog10;
7952ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    }
7962ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//
7972ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller//    private static final double LOG10 = Math.log(10.0);
7982ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
7992ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
8002ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * equality test between two digit lists.
8012ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
8022ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public boolean equals(Object obj) {
8032ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (this == obj)                      // quick check
8042ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return true;
8052ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (!(obj instanceof DigitList))         // (1) same object?
8062ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return false;
8072ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        DigitList other = (DigitList) obj;
8082ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (count != other.count ||
8092ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        decimalAt != other.decimalAt)
8102ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            return false;
8112ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i = 0; i < count; i++)
8122ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            if (digits[i] != other.digits[i])
8132ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller                return false;
8142ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return true;
8152ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
8162ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
8172ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    /**
8182ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     * Generates the hash code for the digit list.
8192ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller     */
8202ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public int hashCode() {
8212ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        int hashcode = decimalAt;
8222ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
8232ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i = 0; i < count; i++)
8242ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller            hashcode = hashcode * 37 + digits[i];
8252ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
8262ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return hashcode;
8272ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
8282ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller
8292ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    public String toString()
8302ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    {
8312ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        if (isZero()) return "0";
8322ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        StringBuilder buf = new StringBuilder("0.");
8332ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        for (int i=0; i<count; ++i) buf.append((char)digits[i]);
8342ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        buf.append("x10^");
8352ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        buf.append(decimalAt);
8362ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller        return buf.toString();
8372ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller    }
8382ae130017183d2f66d55bf0ca51f8da3294644fdNeil Fuller}
839