1 /* 2 * Copyright (c) 1996, 2012, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 /* 27 * (C) Copyright Taligent, Inc. 1996, 1997 - All Rights Reserved 28 * (C) Copyright IBM Corp. 1996 - 1998 - All Rights Reserved 29 * 30 * The original version of this source code and documentation is copyrighted 31 * and owned by Taligent, Inc., a wholly-owned subsidiary of IBM. These 32 * materials are provided under terms of a License Agreement between Taligent 33 * and Sun. This technology is protected by multiple US and International 34 * patents. This notice and attribution to Taligent may not be removed. 35 * Taligent is a registered trademark of Taligent, Inc. 36 * 37 */ 38 39 package java.text; 40 41 import java.io.IOException; 42 import java.io.InvalidObjectException; 43 import java.io.ObjectInputStream; 44 import java.math.BigDecimal; 45 import java.math.BigInteger; 46 import java.math.RoundingMode; 47 import java.text.spi.NumberFormatProvider; 48 import java.util.ArrayList; 49 import java.util.Currency; 50 import java.util.Locale; 51 import java.util.ResourceBundle; 52 import java.util.concurrent.ConcurrentHashMap; 53 import java.util.concurrent.ConcurrentMap; 54 import java.util.concurrent.atomic.AtomicInteger; 55 import java.util.concurrent.atomic.AtomicLong; 56 import sun.util.locale.provider.LocaleProviderAdapter; 57 58 /** 59 * <code>DecimalFormat</code> is a concrete subclass of 60 * <code>NumberFormat</code> that formats decimal numbers. It has a variety of 61 * features designed to make it possible to parse and format numbers in any 62 * locale, including support for Western, Arabic, and Indic digits. It also 63 * supports different kinds of numbers, including integers (123), fixed-point 64 * numbers (123.4), scientific notation (1.23E4), percentages (12%), and 65 * currency amounts ($123). All of these can be localized. 66 * 67 * <p>To obtain a <code>NumberFormat</code> for a specific locale, including the 68 * default locale, call one of <code>NumberFormat</code>'s factory methods, such 69 * as <code>getInstance()</code>. In general, do not call the 70 * <code>DecimalFormat</code> constructors directly, since the 71 * <code>NumberFormat</code> factory methods may return subclasses other than 72 * <code>DecimalFormat</code>. If you need to customize the format object, do 73 * something like this: 74 * 75 * <blockquote><pre> 76 * NumberFormat f = NumberFormat.getInstance(loc); 77 * if (f instanceof DecimalFormat) { 78 * ((DecimalFormat) f).setDecimalSeparatorAlwaysShown(true); 79 * } 80 * </pre></blockquote> 81 * 82 * <p>A <code>DecimalFormat</code> comprises a <em>pattern</em> and a set of 83 * <em>symbols</em>. The pattern may be set directly using 84 * <code>applyPattern()</code>, or indirectly using the API methods. The 85 * symbols are stored in a <code>DecimalFormatSymbols</code> object. When using 86 * the <code>NumberFormat</code> factory methods, the pattern and symbols are 87 * read from localized <code>ResourceBundle</code>s. 88 * 89 * <h4>Patterns</h4> 90 * 91 * <code>DecimalFormat</code> patterns have the following syntax: 92 * <blockquote><pre> 93 * <i>Pattern:</i> 94 * <i>PositivePattern</i> 95 * <i>PositivePattern</i> ; <i>NegativePattern</i> 96 * <i>PositivePattern:</i> 97 * <i>Prefix<sub>opt</sub></i> <i>Number</i> <i>Suffix<sub>opt</sub></i> 98 * <i>NegativePattern:</i> 99 * <i>Prefix<sub>opt</sub></i> <i>Number</i> <i>Suffix<sub>opt</sub></i> 100 * <i>Prefix:</i> 101 * any Unicode characters except \uFFFE, \uFFFF, and special characters 102 * <i>Suffix:</i> 103 * any Unicode characters except \uFFFE, \uFFFF, and special characters 104 * <i>Number:</i> 105 * <i>Integer</i> <i>Exponent<sub>opt</sub></i> 106 * <i>Integer</i> . <i>Fraction</i> <i>Exponent<sub>opt</sub></i> 107 * <i>Integer:</i> 108 * <i>MinimumInteger</i> 109 * # 110 * # <i>Integer</i> 111 * # , <i>Integer</i> 112 * <i>MinimumInteger:</i> 113 * 0 114 * 0 <i>MinimumInteger</i> 115 * 0 , <i>MinimumInteger</i> 116 * <i>Fraction:</i> 117 * <i>MinimumFraction<sub>opt</sub></i> <i>OptionalFraction<sub>opt</sub></i> 118 * <i>MinimumFraction:</i> 119 * 0 <i>MinimumFraction<sub>opt</sub></i> 120 * <i>OptionalFraction:</i> 121 * # <i>OptionalFraction<sub>opt</sub></i> 122 * <i>Exponent:</i> 123 * E <i>MinimumExponent</i> 124 * <i>MinimumExponent:</i> 125 * 0 <i>MinimumExponent<sub>opt</sub></i> 126 * </pre></blockquote> 127 * 128 * <p>A <code>DecimalFormat</code> pattern contains a positive and negative 129 * subpattern, for example, <code>"#,##0.00;(#,##0.00)"</code>. Each 130 * subpattern has a prefix, numeric part, and suffix. The negative subpattern 131 * is optional; if absent, then the positive subpattern prefixed with the 132 * localized minus sign (<code>'-'</code> in most locales) is used as the 133 * negative subpattern. That is, <code>"0.00"</code> alone is equivalent to 134 * <code>"0.00;-0.00"</code>. If there is an explicit negative subpattern, it 135 * serves only to specify the negative prefix and suffix; the number of digits, 136 * minimal digits, and other characteristics are all the same as the positive 137 * pattern. That means that <code>"#,##0.0#;(#)"</code> produces precisely 138 * the same behavior as <code>"#,##0.0#;(#,##0.0#)"</code>. 139 * 140 * <p>The prefixes, suffixes, and various symbols used for infinity, digits, 141 * thousands separators, decimal separators, etc. may be set to arbitrary 142 * values, and they will appear properly during formatting. However, care must 143 * be taken that the symbols and strings do not conflict, or parsing will be 144 * unreliable. For example, either the positive and negative prefixes or the 145 * suffixes must be distinct for <code>DecimalFormat.parse()</code> to be able 146 * to distinguish positive from negative values. (If they are identical, then 147 * <code>DecimalFormat</code> will behave as if no negative subpattern was 148 * specified.) Another example is that the decimal separator and thousands 149 * separator should be distinct characters, or parsing will be impossible. 150 * 151 * <p>The grouping separator is commonly used for thousands, but in some 152 * countries it separates ten-thousands. The grouping size is a constant number 153 * of digits between the grouping characters, such as 3 for 100,000,000 or 4 for 154 * 1,0000,0000. If you supply a pattern with multiple grouping characters, the 155 * interval between the last one and the end of the integer is the one that is 156 * used. So <code>"#,##,###,####"</code> == <code>"######,####"</code> == 157 * <code>"##,####,####"</code>. 158 * 159 * <h4>Special Pattern Characters</h4> 160 * 161 * <p>Many characters in a pattern are taken literally; they are matched during 162 * parsing and output unchanged during formatting. Special characters, on the 163 * other hand, stand for other characters, strings, or classes of characters. 164 * They must be quoted, unless noted otherwise, if they are to appear in the 165 * prefix or suffix as literals. 166 * 167 * <p>The characters listed here are used in non-localized patterns. Localized 168 * patterns use the corresponding characters taken from this formatter's 169 * <code>DecimalFormatSymbols</code> object instead, and these characters lose 170 * their special status. Two exceptions are the currency sign and quote, which 171 * are not localized. 172 * 173 * <blockquote> 174 * <table border=0 cellspacing=3 cellpadding=0 summary="Chart showing symbol, 175 * location, localized, and meaning."> 176 * <tr bgcolor="#ccccff"> 177 * <th align=left>Symbol 178 * <th align=left>Location 179 * <th align=left>Localized? 180 * <th align=left>Meaning 181 * <tr valign=top> 182 * <td><code>0</code> 183 * <td>Number 184 * <td>Yes 185 * <td>Digit 186 * <tr valign=top bgcolor="#eeeeff"> 187 * <td><code>#</code> 188 * <td>Number 189 * <td>Yes 190 * <td>Digit, zero shows as absent 191 * <tr valign=top> 192 * <td><code>.</code> 193 * <td>Number 194 * <td>Yes 195 * <td>Decimal separator or monetary decimal separator 196 * <tr valign=top bgcolor="#eeeeff"> 197 * <td><code>-</code> 198 * <td>Number 199 * <td>Yes 200 * <td>Minus sign 201 * <tr valign=top> 202 * <td><code>,</code> 203 * <td>Number 204 * <td>Yes 205 * <td>Grouping separator 206 * <tr valign=top bgcolor="#eeeeff"> 207 * <td><code>E</code> 208 * <td>Number 209 * <td>Yes 210 * <td>Separates mantissa and exponent in scientific notation. 211 * <em>Need not be quoted in prefix or suffix.</em> 212 * <tr valign=top> 213 * <td><code>;</code> 214 * <td>Subpattern boundary 215 * <td>Yes 216 * <td>Separates positive and negative subpatterns 217 * <tr valign=top bgcolor="#eeeeff"> 218 * <td><code>%</code> 219 * <td>Prefix or suffix 220 * <td>Yes 221 * <td>Multiply by 100 and show as percentage 222 * <tr valign=top> 223 * <td><code>\u2030</code> 224 * <td>Prefix or suffix 225 * <td>Yes 226 * <td>Multiply by 1000 and show as per mille value 227 * <tr valign=top bgcolor="#eeeeff"> 228 * <td><code>¤</code> (<code>\u00A4</code>) 229 * <td>Prefix or suffix 230 * <td>No 231 * <td>Currency sign, replaced by currency symbol. If 232 * doubled, replaced by international currency symbol. 233 * If present in a pattern, the monetary decimal separator 234 * is used instead of the decimal separator. 235 * <tr valign=top> 236 * <td><code>'</code> 237 * <td>Prefix or suffix 238 * <td>No 239 * <td>Used to quote special characters in a prefix or suffix, 240 * for example, <code>"'#'#"</code> formats 123 to 241 * <code>"#123"</code>. To create a single quote 242 * itself, use two in a row: <code>"# o''clock"</code>. 243 * </table> 244 * </blockquote> 245 * 246 * <h4>Scientific Notation</h4> 247 * 248 * <p>Numbers in scientific notation are expressed as the product of a mantissa 249 * and a power of ten, for example, 1234 can be expressed as 1.234 x 10^3. The 250 * mantissa is often in the range 1.0 <= x < 10.0, but it need not be. 251 * <code>DecimalFormat</code> can be instructed to format and parse scientific 252 * notation <em>only via a pattern</em>; there is currently no factory method 253 * that creates a scientific notation format. In a pattern, the exponent 254 * character immediately followed by one or more digit characters indicates 255 * scientific notation. Example: <code>"0.###E0"</code> formats the number 256 * 1234 as <code>"1.234E3"</code>. 257 * 258 * <ul> 259 * <li>The number of digit characters after the exponent character gives the 260 * minimum exponent digit count. There is no maximum. Negative exponents are 261 * formatted using the localized minus sign, <em>not</em> the prefix and suffix 262 * from the pattern. This allows patterns such as <code>"0.###E0 m/s"</code>. 263 * 264 * <li>The minimum and maximum number of integer digits are interpreted 265 * together: 266 * 267 * <ul> 268 * <li>If the maximum number of integer digits is greater than their minimum number 269 * and greater than 1, it forces the exponent to be a multiple of the maximum 270 * number of integer digits, and the minimum number of integer digits to be 271 * interpreted as 1. The most common use of this is to generate 272 * <em>engineering notation</em>, in which the exponent is a multiple of three, 273 * e.g., <code>"##0.#####E0"</code>. Using this pattern, the number 12345 274 * formats to <code>"12.345E3"</code>, and 123456 formats to 275 * <code>"123.456E3"</code>. 276 * 277 * <li>Otherwise, the minimum number of integer digits is achieved by adjusting the 278 * exponent. Example: 0.00123 formatted with <code>"00.###E0"</code> yields 279 * <code>"12.3E-4"</code>. 280 * </ul> 281 * 282 * <li>The number of significant digits in the mantissa is the sum of the 283 * <em>minimum integer</em> and <em>maximum fraction</em> digits, and is 284 * unaffected by the maximum integer digits. For example, 12345 formatted with 285 * <code>"##0.##E0"</code> is <code>"12.3E3"</code>. To show all digits, set 286 * the significant digits count to zero. The number of significant digits 287 * does not affect parsing. 288 * 289 * <li>Exponential patterns may not contain grouping separators. 290 * </ul> 291 * 292 * <h4>Rounding</h4> 293 * 294 * <code>DecimalFormat</code> provides rounding modes defined in 295 * {@link java.math.RoundingMode} for formatting. By default, it uses 296 * {@link java.math.RoundingMode#HALF_EVEN RoundingMode.HALF_EVEN}. 297 * 298 * <h4>Digits</h4> 299 * 300 * For formatting, <code>DecimalFormat</code> uses the ten consecutive 301 * characters starting with the localized zero digit defined in the 302 * <code>DecimalFormatSymbols</code> object as digits. For parsing, these 303 * digits as well as all Unicode decimal digits, as defined by 304 * {@link Character#digit Character.digit}, are recognized. 305 * 306 * <h4>Special Values</h4> 307 * 308 * <p><code>NaN</code> is formatted as a string, which typically has a single character 309 * <code>\uFFFD</code>. This string is determined by the 310 * <code>DecimalFormatSymbols</code> object. This is the only value for which 311 * the prefixes and suffixes are not used. 312 * 313 * <p>Infinity is formatted as a string, which typically has a single character 314 * <code>\u221E</code>, with the positive or negative prefixes and suffixes 315 * applied. The infinity string is determined by the 316 * <code>DecimalFormatSymbols</code> object. 317 * 318 * <p>Negative zero (<code>"-0"</code>) parses to 319 * <ul> 320 * <li><code>BigDecimal(0)</code> if <code>isParseBigDecimal()</code> is 321 * true, 322 * <li><code>Long(0)</code> if <code>isParseBigDecimal()</code> is false 323 * and <code>isParseIntegerOnly()</code> is true, 324 * <li><code>Double(-0.0)</code> if both <code>isParseBigDecimal()</code> 325 * and <code>isParseIntegerOnly()</code> are false. 326 * </ul> 327 * 328 * <h4><a name="synchronization">Synchronization</a></h4> 329 * 330 * <p> 331 * Decimal formats are generally not synchronized. 332 * It is recommended to create separate format instances for each thread. 333 * If multiple threads access a format concurrently, it must be synchronized 334 * externally. 335 * 336 * <h4>Example</h4> 337 * 338 * <blockquote><pre> 339 * <strong>// Print out a number using the localized number, integer, currency, 340 * // and percent format for each locale</strong> 341 * Locale[] locales = NumberFormat.getAvailableLocales(); 342 * double myNumber = -1234.56; 343 * NumberFormat form; 344 * for (int j=0; j<4; ++j) { 345 * System.out.println("FORMAT"); 346 * for (int i = 0; i < locales.length; ++i) { 347 * if (locales[i].getCountry().length() == 0) { 348 * continue; // Skip language-only locales 349 * } 350 * System.out.print(locales[i].getDisplayName()); 351 * switch (j) { 352 * case 0: 353 * form = NumberFormat.getInstance(locales[i]); break; 354 * case 1: 355 * form = NumberFormat.getIntegerInstance(locales[i]); break; 356 * case 2: 357 * form = NumberFormat.getCurrencyInstance(locales[i]); break; 358 * default: 359 * form = NumberFormat.getPercentInstance(locales[i]); break; 360 * } 361 * if (form instanceof DecimalFormat) { 362 * System.out.print(": " + ((DecimalFormat) form).toPattern()); 363 * } 364 * System.out.print(" -> " + form.format(myNumber)); 365 * try { 366 * System.out.println(" -> " + form.parse(form.format(myNumber))); 367 * } catch (ParseException e) {} 368 * } 369 * } 370 * </pre></blockquote> 371 * 372 * @see <a href="http://java.sun.com/docs/books/tutorial/i18n/format/decimalFormat.html">Java Tutorial</a> 373 * @see NumberFormat 374 * @see DecimalFormatSymbols 375 * @see ParsePosition 376 * @author Mark Davis 377 * @author Alan Liu 378 */ 379 public class DecimalFormat extends NumberFormat { 380 381 /** 382 * Creates a DecimalFormat using the default pattern and symbols 383 * for the default locale. This is a convenient way to obtain a 384 * DecimalFormat when internationalization is not the main concern. 385 * <p> 386 * To obtain standard formats for a given locale, use the factory methods 387 * on NumberFormat such as getNumberInstance. These factories will 388 * return the most appropriate sub-class of NumberFormat for a given 389 * locale. 390 * 391 * @see java.text.NumberFormat#getInstance 392 * @see java.text.NumberFormat#getNumberInstance 393 * @see java.text.NumberFormat#getCurrencyInstance 394 * @see java.text.NumberFormat#getPercentInstance 395 */ 396 public DecimalFormat() { 397 Locale def = Locale.getDefault(Locale.Category.FORMAT); 398 // try to get the pattern from the cache 399 String pattern = cachedLocaleData.get(def); 400 if (pattern == null) { /* cache miss */ 401 // Get the pattern for the default locale. 402 LocaleProviderAdapter adapter = LocaleProviderAdapter.getAdapter(NumberFormatProvider.class, def); 403 switch (adapter.getAdapterType()) { 404 case HOST: 405 case SPI: 406 adapter = LocaleProviderAdapter.getResourceBundleBased(); 407 break; 408 } 409 ResourceBundle rb = adapter.getLocaleData().getNumberFormatData(def); 410 String[] all = rb.getStringArray("NumberPatterns"); 411 pattern = all[0]; 412 /* update cache */ 413 cachedLocaleData.putIfAbsent(def, pattern); 414 } 415 416 // Always applyPattern after the symbols are set 417 this.symbols = DecimalFormatSymbols.getInstance(def); 418 applyPattern(pattern, false); 419 } 420 421 422 /** 423 * Creates a DecimalFormat using the given pattern and the symbols 424 * for the default locale. This is a convenient way to obtain a 425 * DecimalFormat when internationalization is not the main concern. 426 * <p> 427 * To obtain standard formats for a given locale, use the factory methods 428 * on NumberFormat such as getNumberInstance. These factories will 429 * return the most appropriate sub-class of NumberFormat for a given 430 * locale. 431 * 432 * @param pattern A non-localized pattern string. 433 * @exception NullPointerException if <code>pattern</code> is null 434 * @exception IllegalArgumentException if the given pattern is invalid. 435 * @see java.text.NumberFormat#getInstance 436 * @see java.text.NumberFormat#getNumberInstance 437 * @see java.text.NumberFormat#getCurrencyInstance 438 * @see java.text.NumberFormat#getPercentInstance 439 */ 440 public DecimalFormat(String pattern) { 441 // Always applyPattern after the symbols are set 442 this.symbols = DecimalFormatSymbols.getInstance(Locale.getDefault(Locale.Category.FORMAT)); 443 applyPattern(pattern, false); 444 } 445 446 447 /** 448 * Creates a DecimalFormat using the given pattern and symbols. 449 * Use this constructor when you need to completely customize the 450 * behavior of the format. 451 * <p> 452 * To obtain standard formats for a given 453 * locale, use the factory methods on NumberFormat such as 454 * getInstance or getCurrencyInstance. If you need only minor adjustments 455 * to a standard format, you can modify the format returned by 456 * a NumberFormat factory method. 457 * 458 * @param pattern a non-localized pattern string 459 * @param symbols the set of symbols to be used 460 * @exception NullPointerException if any of the given arguments is null 461 * @exception IllegalArgumentException if the given pattern is invalid 462 * @see java.text.NumberFormat#getInstance 463 * @see java.text.NumberFormat#getNumberInstance 464 * @see java.text.NumberFormat#getCurrencyInstance 465 * @see java.text.NumberFormat#getPercentInstance 466 * @see java.text.DecimalFormatSymbols 467 */ 468 public DecimalFormat (String pattern, DecimalFormatSymbols symbols) { 469 // Always applyPattern after the symbols are set 470 this.symbols = (DecimalFormatSymbols)symbols.clone(); 471 applyPattern(pattern, false); 472 } 473 474 475 // Overrides 476 /** 477 * Formats a number and appends the resulting text to the given string 478 * buffer. 479 * The number can be of any subclass of {@link java.lang.Number}. 480 * <p> 481 * This implementation uses the maximum precision permitted. 482 * @param number the number to format 483 * @param toAppendTo the <code>StringBuffer</code> to which the formatted 484 * text is to be appended 485 * @param pos On input: an alignment field, if desired. 486 * On output: the offsets of the alignment field. 487 * @return the value passed in as <code>toAppendTo</code> 488 * @exception IllegalArgumentException if <code>number</code> is 489 * null or not an instance of <code>Number</code>. 490 * @exception NullPointerException if <code>toAppendTo</code> or 491 * <code>pos</code> is null 492 * @exception ArithmeticException if rounding is needed with rounding 493 * mode being set to RoundingMode.UNNECESSARY 494 * @see java.text.FieldPosition 495 */ 496 @Override 497 public final StringBuffer format(Object number, 498 StringBuffer toAppendTo, 499 FieldPosition pos) { 500 if (number instanceof Long || number instanceof Integer || 501 number instanceof Short || number instanceof Byte || 502 number instanceof AtomicInteger || 503 number instanceof AtomicLong || 504 (number instanceof BigInteger && 505 ((BigInteger)number).bitLength () < 64)) { 506 return format(((Number)number).longValue(), toAppendTo, pos); 507 } else if (number instanceof BigDecimal) { 508 return format((BigDecimal)number, toAppendTo, pos); 509 } else if (number instanceof BigInteger) { 510 return format((BigInteger)number, toAppendTo, pos); 511 } else if (number instanceof Number) { 512 return format(((Number)number).doubleValue(), toAppendTo, pos); 513 } else { 514 throw new IllegalArgumentException("Cannot format given Object as a Number"); 515 } 516 } 517 518 /** 519 * Formats a double to produce a string. 520 * @param number The double to format 521 * @param result where the text is to be appended 522 * @param fieldPosition On input: an alignment field, if desired. 523 * On output: the offsets of the alignment field. 524 * @exception ArithmeticException if rounding is needed with rounding 525 * mode being set to RoundingMode.UNNECESSARY 526 * @return The formatted number string 527 * @see java.text.FieldPosition 528 */ 529 @Override 530 public StringBuffer format(double number, StringBuffer result, 531 FieldPosition fieldPosition) { 532 // If fieldPosition is a DontCareFieldPosition instance we can 533 // try to go to fast-path code. 534 boolean tryFastPath = false; 535 if (fieldPosition == DontCareFieldPosition.INSTANCE) 536 tryFastPath = true; 537 else { 538 fieldPosition.setBeginIndex(0); 539 fieldPosition.setEndIndex(0); 540 } 541 542 if (tryFastPath) { 543 String tempResult = fastFormat(number); 544 if (tempResult != null) { 545 result.append(tempResult); 546 return result; 547 } 548 } 549 550 // if fast-path could not work, we fallback to standard code. 551 return format(number, result, fieldPosition.getFieldDelegate()); 552 } 553 554 /** 555 * Formats a double to produce a string. 556 * @param number The double to format 557 * @param result where the text is to be appended 558 * @param delegate notified of locations of sub fields 559 * @exception ArithmeticException if rounding is needed with rounding 560 * mode being set to RoundingMode.UNNECESSARY 561 * @return The formatted number string 562 */ 563 private StringBuffer format(double number, StringBuffer result, 564 FieldDelegate delegate) { 565 if (Double.isNaN(number) || 566 (Double.isInfinite(number) && multiplier == 0)) { 567 int iFieldStart = result.length(); 568 result.append(symbols.getNaN()); 569 delegate.formatted(INTEGER_FIELD, Field.INTEGER, Field.INTEGER, 570 iFieldStart, result.length(), result); 571 return result; 572 } 573 574 /* Detecting whether a double is negative is easy with the exception of 575 * the value -0.0. This is a double which has a zero mantissa (and 576 * exponent), but a negative sign bit. It is semantically distinct from 577 * a zero with a positive sign bit, and this distinction is important 578 * to certain kinds of computations. However, it's a little tricky to 579 * detect, since (-0.0 == 0.0) and !(-0.0 < 0.0). How then, you may 580 * ask, does it behave distinctly from +0.0? Well, 1/(-0.0) == 581 * -Infinity. Proper detection of -0.0 is needed to deal with the 582 * issues raised by bugs 4106658, 4106667, and 4147706. Liu 7/6/98. 583 */ 584 boolean isNegative = ((number < 0.0) || (number == 0.0 && 1/number < 0.0)) ^ (multiplier < 0); 585 586 if (multiplier != 1) { 587 number *= multiplier; 588 } 589 590 if (Double.isInfinite(number)) { 591 if (isNegative) { 592 append(result, negativePrefix, delegate, 593 getNegativePrefixFieldPositions(), Field.SIGN); 594 } else { 595 append(result, positivePrefix, delegate, 596 getPositivePrefixFieldPositions(), Field.SIGN); 597 } 598 599 int iFieldStart = result.length(); 600 result.append(symbols.getInfinity()); 601 delegate.formatted(INTEGER_FIELD, Field.INTEGER, Field.INTEGER, 602 iFieldStart, result.length(), result); 603 604 if (isNegative) { 605 append(result, negativeSuffix, delegate, 606 getNegativeSuffixFieldPositions(), Field.SIGN); 607 } else { 608 append(result, positiveSuffix, delegate, 609 getPositiveSuffixFieldPositions(), Field.SIGN); 610 } 611 612 return result; 613 } 614 615 if (isNegative) { 616 number = -number; 617 } 618 619 // at this point we are guaranteed a nonnegative finite number. 620 assert(number >= 0 && !Double.isInfinite(number)); 621 622 synchronized(digitList) { 623 int maxIntDigits = super.getMaximumIntegerDigits(); 624 int minIntDigits = super.getMinimumIntegerDigits(); 625 int maxFraDigits = super.getMaximumFractionDigits(); 626 int minFraDigits = super.getMinimumFractionDigits(); 627 628 digitList.set(isNegative, number, useExponentialNotation ? 629 maxIntDigits + maxFraDigits : maxFraDigits, 630 !useExponentialNotation); 631 return subformat(result, delegate, isNegative, false, 632 maxIntDigits, minIntDigits, maxFraDigits, minFraDigits); 633 } 634 } 635 636 /** 637 * Format a long to produce a string. 638 * @param number The long to format 639 * @param result where the text is to be appended 640 * @param fieldPosition On input: an alignment field, if desired. 641 * On output: the offsets of the alignment field. 642 * @exception ArithmeticException if rounding is needed with rounding 643 * mode being set to RoundingMode.UNNECESSARY 644 * @return The formatted number string 645 * @see java.text.FieldPosition 646 */ 647 @Override 648 public StringBuffer format(long number, StringBuffer result, 649 FieldPosition fieldPosition) { 650 fieldPosition.setBeginIndex(0); 651 fieldPosition.setEndIndex(0); 652 653 return format(number, result, fieldPosition.getFieldDelegate()); 654 } 655 656 /** 657 * Format a long to produce a string. 658 * @param number The long to format 659 * @param result where the text is to be appended 660 * @param delegate notified of locations of sub fields 661 * @return The formatted number string 662 * @exception ArithmeticException if rounding is needed with rounding 663 * mode being set to RoundingMode.UNNECESSARY 664 * @see java.text.FieldPosition 665 */ 666 private StringBuffer format(long number, StringBuffer result, 667 FieldDelegate delegate) { 668 boolean isNegative = (number < 0); 669 if (isNegative) { 670 number = -number; 671 } 672 673 // In general, long values always represent real finite numbers, so 674 // we don't have to check for +/- Infinity or NaN. However, there 675 // is one case we have to be careful of: The multiplier can push 676 // a number near MIN_VALUE or MAX_VALUE outside the legal range. We 677 // check for this before multiplying, and if it happens we use 678 // BigInteger instead. 679 boolean useBigInteger = false; 680 if (number < 0) { // This can only happen if number == Long.MIN_VALUE. 681 if (multiplier != 0) { 682 useBigInteger = true; 683 } 684 } else if (multiplier != 1 && multiplier != 0) { 685 long cutoff = Long.MAX_VALUE / multiplier; 686 if (cutoff < 0) { 687 cutoff = -cutoff; 688 } 689 useBigInteger = (number > cutoff); 690 } 691 692 if (useBigInteger) { 693 if (isNegative) { 694 number = -number; 695 } 696 BigInteger bigIntegerValue = BigInteger.valueOf(number); 697 return format(bigIntegerValue, result, delegate, true); 698 } 699 700 number *= multiplier; 701 if (number == 0) { 702 isNegative = false; 703 } else { 704 if (multiplier < 0) { 705 number = -number; 706 isNegative = !isNegative; 707 } 708 } 709 710 synchronized(digitList) { 711 int maxIntDigits = super.getMaximumIntegerDigits(); 712 int minIntDigits = super.getMinimumIntegerDigits(); 713 int maxFraDigits = super.getMaximumFractionDigits(); 714 int minFraDigits = super.getMinimumFractionDigits(); 715 716 digitList.set(isNegative, number, 717 useExponentialNotation ? maxIntDigits + maxFraDigits : 0); 718 719 return subformat(result, delegate, isNegative, true, 720 maxIntDigits, minIntDigits, maxFraDigits, minFraDigits); 721 } 722 } 723 724 /** 725 * Formats a BigDecimal to produce a string. 726 * @param number The BigDecimal to format 727 * @param result where the text is to be appended 728 * @param fieldPosition On input: an alignment field, if desired. 729 * On output: the offsets of the alignment field. 730 * @return The formatted number string 731 * @exception ArithmeticException if rounding is needed with rounding 732 * mode being set to RoundingMode.UNNECESSARY 733 * @see java.text.FieldPosition 734 */ 735 private StringBuffer format(BigDecimal number, StringBuffer result, 736 FieldPosition fieldPosition) { 737 fieldPosition.setBeginIndex(0); 738 fieldPosition.setEndIndex(0); 739 return format(number, result, fieldPosition.getFieldDelegate()); 740 } 741 742 /** 743 * Formats a BigDecimal to produce a string. 744 * @param number The BigDecimal to format 745 * @param result where the text is to be appended 746 * @param delegate notified of locations of sub fields 747 * @exception ArithmeticException if rounding is needed with rounding 748 * mode being set to RoundingMode.UNNECESSARY 749 * @return The formatted number string 750 */ 751 private StringBuffer format(BigDecimal number, StringBuffer result, 752 FieldDelegate delegate) { 753 if (multiplier != 1) { 754 number = number.multiply(getBigDecimalMultiplier()); 755 } 756 boolean isNegative = number.signum() == -1; 757 if (isNegative) { 758 number = number.negate(); 759 } 760 761 synchronized(digitList) { 762 int maxIntDigits = getMaximumIntegerDigits(); 763 int minIntDigits = getMinimumIntegerDigits(); 764 int maxFraDigits = getMaximumFractionDigits(); 765 int minFraDigits = getMinimumFractionDigits(); 766 int maximumDigits = maxIntDigits + maxFraDigits; 767 768 digitList.set(isNegative, number, useExponentialNotation ? 769 ((maximumDigits < 0) ? Integer.MAX_VALUE : maximumDigits) : 770 maxFraDigits, !useExponentialNotation); 771 772 return subformat(result, delegate, isNegative, false, 773 maxIntDigits, minIntDigits, maxFraDigits, minFraDigits); 774 } 775 } 776 777 /** 778 * Format a BigInteger to produce a string. 779 * @param number The BigInteger to format 780 * @param result where the text is to be appended 781 * @param fieldPosition On input: an alignment field, if desired. 782 * On output: the offsets of the alignment field. 783 * @return The formatted number string 784 * @exception ArithmeticException if rounding is needed with rounding 785 * mode being set to RoundingMode.UNNECESSARY 786 * @see java.text.FieldPosition 787 */ 788 private StringBuffer format(BigInteger number, StringBuffer result, 789 FieldPosition fieldPosition) { 790 fieldPosition.setBeginIndex(0); 791 fieldPosition.setEndIndex(0); 792 793 return format(number, result, fieldPosition.getFieldDelegate(), false); 794 } 795 796 /** 797 * Format a BigInteger to produce a string. 798 * @param number The BigInteger to format 799 * @param result where the text is to be appended 800 * @param delegate notified of locations of sub fields 801 * @return The formatted number string 802 * @exception ArithmeticException if rounding is needed with rounding 803 * mode being set to RoundingMode.UNNECESSARY 804 * @see java.text.FieldPosition 805 */ 806 private StringBuffer format(BigInteger number, StringBuffer result, 807 FieldDelegate delegate, boolean formatLong) { 808 if (multiplier != 1) { 809 number = number.multiply(getBigIntegerMultiplier()); 810 } 811 boolean isNegative = number.signum() == -1; 812 if (isNegative) { 813 number = number.negate(); 814 } 815 816 synchronized(digitList) { 817 int maxIntDigits, minIntDigits, maxFraDigits, minFraDigits, maximumDigits; 818 if (formatLong) { 819 maxIntDigits = super.getMaximumIntegerDigits(); 820 minIntDigits = super.getMinimumIntegerDigits(); 821 maxFraDigits = super.getMaximumFractionDigits(); 822 minFraDigits = super.getMinimumFractionDigits(); 823 maximumDigits = maxIntDigits + maxFraDigits; 824 } else { 825 maxIntDigits = getMaximumIntegerDigits(); 826 minIntDigits = getMinimumIntegerDigits(); 827 maxFraDigits = getMaximumFractionDigits(); 828 minFraDigits = getMinimumFractionDigits(); 829 maximumDigits = maxIntDigits + maxFraDigits; 830 if (maximumDigits < 0) { 831 maximumDigits = Integer.MAX_VALUE; 832 } 833 } 834 835 digitList.set(isNegative, number, 836 useExponentialNotation ? maximumDigits : 0); 837 838 return subformat(result, delegate, isNegative, true, 839 maxIntDigits, minIntDigits, maxFraDigits, minFraDigits); 840 } 841 } 842 843 /** 844 * Formats an Object producing an <code>AttributedCharacterIterator</code>. 845 * You can use the returned <code>AttributedCharacterIterator</code> 846 * to build the resulting String, as well as to determine information 847 * about the resulting String. 848 * <p> 849 * Each attribute key of the AttributedCharacterIterator will be of type 850 * <code>NumberFormat.Field</code>, with the attribute value being the 851 * same as the attribute key. 852 * 853 * @exception NullPointerException if obj is null. 854 * @exception IllegalArgumentException when the Format cannot format the 855 * given object. 856 * @exception ArithmeticException if rounding is needed with rounding 857 * mode being set to RoundingMode.UNNECESSARY 858 * @param obj The object to format 859 * @return AttributedCharacterIterator describing the formatted value. 860 * @since 1.4 861 */ 862 @Override 863 public AttributedCharacterIterator formatToCharacterIterator(Object obj) { 864 CharacterIteratorFieldDelegate delegate = 865 new CharacterIteratorFieldDelegate(); 866 StringBuffer sb = new StringBuffer(); 867 868 if (obj instanceof Double || obj instanceof Float) { 869 format(((Number)obj).doubleValue(), sb, delegate); 870 } else if (obj instanceof Long || obj instanceof Integer || 871 obj instanceof Short || obj instanceof Byte || 872 obj instanceof AtomicInteger || obj instanceof AtomicLong) { 873 format(((Number)obj).longValue(), sb, delegate); 874 } else if (obj instanceof BigDecimal) { 875 format((BigDecimal)obj, sb, delegate); 876 } else if (obj instanceof BigInteger) { 877 format((BigInteger)obj, sb, delegate, false); 878 } else if (obj == null) { 879 throw new NullPointerException( 880 "formatToCharacterIterator must be passed non-null object"); 881 } else { 882 throw new IllegalArgumentException( 883 "Cannot format given Object as a Number"); 884 } 885 return delegate.getIterator(sb.toString()); 886 } 887 888 // ==== Begin fast-path formating logic for double ========================= 889 890 /* Fast-path formatting will be used for format(double ...) methods iff a 891 * number of conditions are met (see checkAndSetFastPathStatus()): 892 * - Only if instance properties meet the right predefined conditions. 893 * - The abs value of the double to format is <= Integer.MAX_VALUE. 894 * 895 * The basic approach is to split the binary to decimal conversion of a 896 * double value into two phases: 897 * * The conversion of the integer portion of the double. 898 * * The conversion of the fractional portion of the double 899 * (limited to two or three digits). 900 * 901 * The isolation and conversion of the integer portion of the double is 902 * straightforward. The conversion of the fraction is more subtle and relies 903 * on some rounding properties of double to the decimal precisions in 904 * question. Using the terminology of BigDecimal, this fast-path algorithm 905 * is applied when a double value has a magnitude less than Integer.MAX_VALUE 906 * and rounding is to nearest even and the destination format has two or 907 * three digits of *scale* (digits after the decimal point). 908 * 909 * Under a rounding to nearest even policy, the returned result is a digit 910 * string of a number in the (in this case decimal) destination format 911 * closest to the exact numerical value of the (in this case binary) input 912 * value. If two destination format numbers are equally distant, the one 913 * with the last digit even is returned. To compute such a correctly rounded 914 * value, some information about digits beyond the smallest returned digit 915 * position needs to be consulted. 916 * 917 * In general, a guard digit, a round digit, and a sticky *bit* are needed 918 * beyond the returned digit position. If the discarded portion of the input 919 * is sufficiently large, the returned digit string is incremented. In round 920 * to nearest even, this threshold to increment occurs near the half-way 921 * point between digits. The sticky bit records if there are any remaining 922 * trailing digits of the exact input value in the new format; the sticky bit 923 * is consulted only in close to half-way rounding cases. 924 * 925 * Given the computation of the digit and bit values, rounding is then 926 * reduced to a table lookup problem. For decimal, the even/odd cases look 927 * like this: 928 * 929 * Last Round Sticky 930 * 6 5 0 => 6 // exactly halfway, return even digit. 931 * 6 5 1 => 7 // a little bit more than halfway, round up. 932 * 7 5 0 => 8 // exactly halfway, round up to even. 933 * 7 5 1 => 8 // a little bit more than halfway, round up. 934 * With analogous entries for other even and odd last-returned digits. 935 * 936 * However, decimal negative powers of 5 smaller than 0.5 are *not* exactly 937 * representable as binary fraction. In particular, 0.005 (the round limit 938 * for a two-digit scale) and 0.0005 (the round limit for a three-digit 939 * scale) are not representable. Therefore, for input values near these cases 940 * the sticky bit is known to be set which reduces the rounding logic to: 941 * 942 * Last Round Sticky 943 * 6 5 1 => 7 // a little bit more than halfway, round up. 944 * 7 5 1 => 8 // a little bit more than halfway, round up. 945 * 946 * In other words, if the round digit is 5, the sticky bit is known to be 947 * set. If the round digit is something other than 5, the sticky bit is not 948 * relevant. Therefore, some of the logic about whether or not to increment 949 * the destination *decimal* value can occur based on tests of *binary* 950 * computations of the binary input number. 951 */ 952 953 /** 954 * Check validity of using fast-path for this instance. If fast-path is valid 955 * for this instance, sets fast-path state as true and initializes fast-path 956 * utility fields as needed. 957 * 958 * This method is supposed to be called rarely, otherwise that will break the 959 * fast-path performance. That means avoiding frequent changes of the 960 * properties of the instance, since for most properties, each time a change 961 * happens, a call to this method is needed at the next format call. 962 * 963 * FAST-PATH RULES: 964 * Similar to the default DecimalFormat instantiation case. 965 * More precisely: 966 * - HALF_EVEN rounding mode, 967 * - isGroupingUsed() is true, 968 * - groupingSize of 3, 969 * - multiplier is 1, 970 * - Decimal separator not mandatory, 971 * - No use of exponential notation, 972 * - minimumIntegerDigits is exactly 1 and maximumIntegerDigits at least 10 973 * - For number of fractional digits, the exact values found in the default case: 974 * Currency : min = max = 2. 975 * Decimal : min = 0. max = 3. 976 * 977 */ 978 private void checkAndSetFastPathStatus() { 979 980 boolean fastPathWasOn = isFastPath; 981 982 if ((roundingMode == RoundingMode.HALF_EVEN) && 983 (isGroupingUsed()) && 984 (groupingSize == 3) && 985 (multiplier == 1) && 986 (!decimalSeparatorAlwaysShown) && 987 (!useExponentialNotation)) { 988 989 // The fast-path algorithm is semi-hardcoded against 990 // minimumIntegerDigits and maximumIntegerDigits. 991 isFastPath = ((minimumIntegerDigits == 1) && 992 (maximumIntegerDigits >= 10)); 993 994 // The fast-path algorithm is hardcoded against 995 // minimumFractionDigits and maximumFractionDigits. 996 if (isFastPath) { 997 if (isCurrencyFormat) { 998 if ((minimumFractionDigits != 2) || 999 (maximumFractionDigits != 2)) 1000 isFastPath = false; 1001 } else if ((minimumFractionDigits != 0) || 1002 (maximumFractionDigits != 3)) 1003 isFastPath = false; 1004 } 1005 } else 1006 isFastPath = false; 1007 1008 // Since some instance properties may have changed while still falling 1009 // in the fast-path case, we need to reinitialize fastPathData anyway. 1010 if (isFastPath) { 1011 // We need to instantiate fastPathData if not already done. 1012 if (fastPathData == null) 1013 fastPathData = new FastPathData(); 1014 1015 // Sets up the locale specific constants used when formatting. 1016 // '0' is our default representation of zero. 1017 fastPathData.zeroDelta = symbols.getZeroDigit() - '0'; 1018 fastPathData.groupingChar = symbols.getGroupingSeparator(); 1019 1020 // Sets up fractional constants related to currency/decimal pattern. 1021 fastPathData.fractionalMaxIntBound = (isCurrencyFormat) ? 99 : 999; 1022 fastPathData.fractionalScaleFactor = (isCurrencyFormat) ? 100.0d : 1000.0d; 1023 1024 // Records the need for adding prefix or suffix 1025 fastPathData.positiveAffixesRequired = 1026 (positivePrefix.length() != 0) || (positiveSuffix.length() != 0); 1027 fastPathData.negativeAffixesRequired = 1028 (negativePrefix.length() != 0) || (negativeSuffix.length() != 0); 1029 1030 // Creates a cached char container for result, with max possible size. 1031 int maxNbIntegralDigits = 10; 1032 int maxNbGroups = 3; 1033 int containerSize = 1034 Math.max(positivePrefix.length(), negativePrefix.length()) + 1035 maxNbIntegralDigits + maxNbGroups + 1 + maximumFractionDigits + 1036 Math.max(positiveSuffix.length(), negativeSuffix.length()); 1037 1038 fastPathData.fastPathContainer = new char[containerSize]; 1039 1040 // Sets up prefix and suffix char arrays constants. 1041 fastPathData.charsPositiveSuffix = positiveSuffix.toCharArray(); 1042 fastPathData.charsNegativeSuffix = negativeSuffix.toCharArray(); 1043 fastPathData.charsPositivePrefix = positivePrefix.toCharArray(); 1044 fastPathData.charsNegativePrefix = negativePrefix.toCharArray(); 1045 1046 // Sets up fixed index positions for integral and fractional digits. 1047 // Sets up decimal point in cached result container. 1048 int longestPrefixLength = 1049 Math.max(positivePrefix.length(), negativePrefix.length()); 1050 int decimalPointIndex = 1051 maxNbIntegralDigits + maxNbGroups + longestPrefixLength; 1052 1053 fastPathData.integralLastIndex = decimalPointIndex - 1; 1054 fastPathData.fractionalFirstIndex = decimalPointIndex + 1; 1055 fastPathData.fastPathContainer[decimalPointIndex] = 1056 isCurrencyFormat ? 1057 symbols.getMonetaryDecimalSeparator() : 1058 symbols.getDecimalSeparator(); 1059 1060 } else if (fastPathWasOn) { 1061 // Previous state was fast-path and is no more. 1062 // Resets cached array constants. 1063 fastPathData.fastPathContainer = null; 1064 fastPathData.charsPositiveSuffix = null; 1065 fastPathData.charsNegativeSuffix = null; 1066 fastPathData.charsPositivePrefix = null; 1067 fastPathData.charsNegativePrefix = null; 1068 } 1069 1070 fastPathCheckNeeded = false; 1071 } 1072 1073 /** 1074 * Returns true if rounding-up must be done on {@code scaledFractionalPartAsInt}, 1075 * false otherwise. 1076 * 1077 * This is a utility method that takes correct half-even rounding decision on 1078 * passed fractional value at the scaled decimal point (2 digits for currency 1079 * case and 3 for decimal case), when the approximated fractional part after 1080 * scaled decimal point is exactly 0.5d. This is done by means of exact 1081 * calculations on the {@code fractionalPart} floating-point value. 1082 * 1083 * This method is supposed to be called by private {@code fastDoubleFormat} 1084 * method only. 1085 * 1086 * The algorithms used for the exact calculations are : 1087 * 1088 * The <b><i>FastTwoSum</i></b> algorithm, from T.J.Dekker, described in the 1089 * papers "<i>A Floating-Point Technique for Extending the Available 1090 * Precision</i>" by Dekker, and in "<i>Adaptive Precision Floating-Point 1091 * Arithmetic and Fast Robust Geometric Predicates</i>" from J.Shewchuk. 1092 * 1093 * A modified version of <b><i>Sum2S</i></b> cascaded summation described in 1094 * "<i>Accurate Sum and Dot Product</i>" from Takeshi Ogita and All. As 1095 * Ogita says in this paper this is an equivalent of the Kahan-Babuska's 1096 * summation algorithm because we order the terms by magnitude before summing 1097 * them. For this reason we can use the <i>FastTwoSum</i> algorithm rather 1098 * than the more expensive Knuth's <i>TwoSum</i>. 1099 * 1100 * We do this to avoid a more expensive exact "<i>TwoProduct</i>" algorithm, 1101 * like those described in Shewchuk's paper above. See comments in the code 1102 * below. 1103 * 1104 * @param fractionalPart The fractional value on which we take rounding 1105 * decision. 1106 * @param scaledFractionalPartAsInt The integral part of the scaled 1107 * fractional value. 1108 * 1109 * @return the decision that must be taken regarding half-even rounding. 1110 */ 1111 private boolean exactRoundUp(double fractionalPart, 1112 int scaledFractionalPartAsInt) { 1113 1114 /* exactRoundUp() method is called by fastDoubleFormat() only. 1115 * The precondition expected to be verified by the passed parameters is : 1116 * scaledFractionalPartAsInt == 1117 * (int) (fractionalPart * fastPathData.fractionalScaleFactor). 1118 * This is ensured by fastDoubleFormat() code. 1119 */ 1120 1121 /* We first calculate roundoff error made by fastDoubleFormat() on 1122 * the scaled fractional part. We do this with exact calculation on the 1123 * passed fractionalPart. Rounding decision will then be taken from roundoff. 1124 */ 1125 1126 /* ---- TwoProduct(fractionalPart, scale factor (i.e. 1000.0d or 100.0d)). 1127 * 1128 * The below is an optimized exact "TwoProduct" calculation of passed 1129 * fractional part with scale factor, using Ogita's Sum2S cascaded 1130 * summation adapted as Kahan-Babuska equivalent by using FastTwoSum 1131 * (much faster) rather than Knuth's TwoSum. 1132 * 1133 * We can do this because we order the summation from smallest to 1134 * greatest, so that FastTwoSum can be used without any additional error. 1135 * 1136 * The "TwoProduct" exact calculation needs 17 flops. We replace this by 1137 * a cascaded summation of FastTwoSum calculations, each involving an 1138 * exact multiply by a power of 2. 1139 * 1140 * Doing so saves overall 4 multiplications and 1 addition compared to 1141 * using traditional "TwoProduct". 1142 * 1143 * The scale factor is either 100 (currency case) or 1000 (decimal case). 1144 * - when 1000, we replace it by (1024 - 16 - 8) = 1000. 1145 * - when 100, we replace it by (128 - 32 + 4) = 100. 1146 * Every multiplication by a power of 2 (1024, 128, 32, 16, 8, 4) is exact. 1147 * 1148 */ 1149 double approxMax; // Will always be positive. 1150 double approxMedium; // Will always be negative. 1151 double approxMin; 1152 1153 double fastTwoSumApproximation = 0.0d; 1154 double fastTwoSumRoundOff = 0.0d; 1155 double bVirtual = 0.0d; 1156 1157 if (isCurrencyFormat) { 1158 // Scale is 100 = 128 - 32 + 4. 1159 // Multiply by 2**n is a shift. No roundoff. No error. 1160 approxMax = fractionalPart * 128.00d; 1161 approxMedium = - (fractionalPart * 32.00d); 1162 approxMin = fractionalPart * 4.00d; 1163 } else { 1164 // Scale is 1000 = 1024 - 16 - 8. 1165 // Multiply by 2**n is a shift. No roundoff. No error. 1166 approxMax = fractionalPart * 1024.00d; 1167 approxMedium = - (fractionalPart * 16.00d); 1168 approxMin = - (fractionalPart * 8.00d); 1169 } 1170 1171 // Shewchuk/Dekker's FastTwoSum(approxMedium, approxMin). 1172 assert(-approxMedium >= Math.abs(approxMin)); 1173 fastTwoSumApproximation = approxMedium + approxMin; 1174 bVirtual = fastTwoSumApproximation - approxMedium; 1175 fastTwoSumRoundOff = approxMin - bVirtual; 1176 double approxS1 = fastTwoSumApproximation; 1177 double roundoffS1 = fastTwoSumRoundOff; 1178 1179 // Shewchuk/Dekker's FastTwoSum(approxMax, approxS1); 1180 assert(approxMax >= Math.abs(approxS1)); 1181 fastTwoSumApproximation = approxMax + approxS1; 1182 bVirtual = fastTwoSumApproximation - approxMax; 1183 fastTwoSumRoundOff = approxS1 - bVirtual; 1184 double roundoff1000 = fastTwoSumRoundOff; 1185 double approx1000 = fastTwoSumApproximation; 1186 double roundoffTotal = roundoffS1 + roundoff1000; 1187 1188 // Shewchuk/Dekker's FastTwoSum(approx1000, roundoffTotal); 1189 assert(approx1000 >= Math.abs(roundoffTotal)); 1190 fastTwoSumApproximation = approx1000 + roundoffTotal; 1191 bVirtual = fastTwoSumApproximation - approx1000; 1192 1193 // Now we have got the roundoff for the scaled fractional 1194 double scaledFractionalRoundoff = roundoffTotal - bVirtual; 1195 1196 // ---- TwoProduct(fractionalPart, scale (i.e. 1000.0d or 100.0d)) end. 1197 1198 /* ---- Taking the rounding decision 1199 * 1200 * We take rounding decision based on roundoff and half-even rounding 1201 * rule. 1202 * 1203 * The above TwoProduct gives us the exact roundoff on the approximated 1204 * scaled fractional, and we know that this approximation is exactly 1205 * 0.5d, since that has already been tested by the caller 1206 * (fastDoubleFormat). 1207 * 1208 * Decision comes first from the sign of the calculated exact roundoff. 1209 * - Since being exact roundoff, it cannot be positive with a scaled 1210 * fractional less than 0.5d, as well as negative with a scaled 1211 * fractional greater than 0.5d. That leaves us with following 3 cases. 1212 * - positive, thus scaled fractional == 0.500....0fff ==> round-up. 1213 * - negative, thus scaled fractional == 0.499....9fff ==> don't round-up. 1214 * - is zero, thus scaled fractioanl == 0.5 ==> half-even rounding applies : 1215 * we round-up only if the integral part of the scaled fractional is odd. 1216 * 1217 */ 1218 if (scaledFractionalRoundoff > 0.0) { 1219 return true; 1220 } else if (scaledFractionalRoundoff < 0.0) { 1221 return false; 1222 } else if ((scaledFractionalPartAsInt & 1) != 0) { 1223 return true; 1224 } 1225 1226 return false; 1227 1228 // ---- Taking the rounding decision end 1229 } 1230 1231 /** 1232 * Collects integral digits from passed {@code number}, while setting 1233 * grouping chars as needed. Updates {@code firstUsedIndex} accordingly. 1234 * 1235 * Loops downward starting from {@code backwardIndex} position (inclusive). 1236 * 1237 * @param number The int value from which we collect digits. 1238 * @param digitsBuffer The char array container where digits and grouping chars 1239 * are stored. 1240 * @param backwardIndex the position from which we start storing digits in 1241 * digitsBuffer. 1242 * 1243 */ 1244 private void collectIntegralDigits(int number, 1245 char[] digitsBuffer, 1246 int backwardIndex) { 1247 int index = backwardIndex; 1248 int q; 1249 int r; 1250 while (number > 999) { 1251 // Generates 3 digits per iteration. 1252 q = number / 1000; 1253 r = number - (q << 10) + (q << 4) + (q << 3); // -1024 +16 +8 = 1000. 1254 number = q; 1255 1256 digitsBuffer[index--] = DigitArrays.DigitOnes1000[r]; 1257 digitsBuffer[index--] = DigitArrays.DigitTens1000[r]; 1258 digitsBuffer[index--] = DigitArrays.DigitHundreds1000[r]; 1259 digitsBuffer[index--] = fastPathData.groupingChar; 1260 } 1261 1262 // Collects last 3 or less digits. 1263 digitsBuffer[index] = DigitArrays.DigitOnes1000[number]; 1264 if (number > 9) { 1265 digitsBuffer[--index] = DigitArrays.DigitTens1000[number]; 1266 if (number > 99) 1267 digitsBuffer[--index] = DigitArrays.DigitHundreds1000[number]; 1268 } 1269 1270 fastPathData.firstUsedIndex = index; 1271 } 1272 1273 /** 1274 * Collects the 2 (currency) or 3 (decimal) fractional digits from passed 1275 * {@code number}, starting at {@code startIndex} position 1276 * inclusive. There is no punctuation to set here (no grouping chars). 1277 * Updates {@code fastPathData.lastFreeIndex} accordingly. 1278 * 1279 * 1280 * @param number The int value from which we collect digits. 1281 * @param digitsBuffer The char array container where digits are stored. 1282 * @param startIndex the position from which we start storing digits in 1283 * digitsBuffer. 1284 * 1285 */ 1286 private void collectFractionalDigits(int number, 1287 char[] digitsBuffer, 1288 int startIndex) { 1289 int index = startIndex; 1290 1291 char digitOnes = DigitArrays.DigitOnes1000[number]; 1292 char digitTens = DigitArrays.DigitTens1000[number]; 1293 1294 if (isCurrencyFormat) { 1295 // Currency case. Always collects fractional digits. 1296 digitsBuffer[index++] = digitTens; 1297 digitsBuffer[index++] = digitOnes; 1298 } else if (number != 0) { 1299 // Decimal case. Hundreds will always be collected 1300 digitsBuffer[index++] = DigitArrays.DigitHundreds1000[number]; 1301 1302 // Ending zeros won't be collected. 1303 if (digitOnes != '0') { 1304 digitsBuffer[index++] = digitTens; 1305 digitsBuffer[index++] = digitOnes; 1306 } else if (digitTens != '0') 1307 digitsBuffer[index++] = digitTens; 1308 1309 } else 1310 // This is decimal pattern and fractional part is zero. 1311 // We must remove decimal point from result. 1312 index--; 1313 1314 fastPathData.lastFreeIndex = index; 1315 } 1316 1317 /** 1318 * Internal utility. 1319 * Adds the passed {@code prefix} and {@code suffix} to {@code container}. 1320 * 1321 * @param container Char array container which to prepend/append the 1322 * prefix/suffix. 1323 * @param prefix Char sequence to prepend as a prefix. 1324 * @param suffix Char sequence to append as a suffix. 1325 * 1326 */ 1327 // private void addAffixes(boolean isNegative, char[] container) { 1328 private void addAffixes(char[] container, char[] prefix, char[] suffix) { 1329 1330 // We add affixes only if needed (affix length > 0). 1331 int pl = prefix.length; 1332 int sl = suffix.length; 1333 if (pl != 0) prependPrefix(prefix, pl, container); 1334 if (sl != 0) appendSuffix(suffix, sl, container); 1335 1336 } 1337 1338 /** 1339 * Prepends the passed {@code prefix} chars to given result 1340 * {@code container}. Updates {@code fastPathData.firstUsedIndex} 1341 * accordingly. 1342 * 1343 * @param prefix The prefix characters to prepend to result. 1344 * @param len The number of chars to prepend. 1345 * @param container Char array container which to prepend the prefix 1346 */ 1347 private void prependPrefix(char[] prefix, 1348 int len, 1349 char[] container) { 1350 1351 fastPathData.firstUsedIndex -= len; 1352 int startIndex = fastPathData.firstUsedIndex; 1353 1354 // If prefix to prepend is only 1 char long, just assigns this char. 1355 // If prefix is less or equal 4, we use a dedicated algorithm that 1356 // has shown to run faster than System.arraycopy. 1357 // If more than 4, we use System.arraycopy. 1358 if (len == 1) 1359 container[startIndex] = prefix[0]; 1360 else if (len <= 4) { 1361 int dstLower = startIndex; 1362 int dstUpper = dstLower + len - 1; 1363 int srcUpper = len - 1; 1364 container[dstLower] = prefix[0]; 1365 container[dstUpper] = prefix[srcUpper]; 1366 1367 if (len > 2) 1368 container[++dstLower] = prefix[1]; 1369 if (len == 4) 1370 container[--dstUpper] = prefix[2]; 1371 } else 1372 System.arraycopy(prefix, 0, container, startIndex, len); 1373 } 1374 1375 /** 1376 * Appends the passed {@code suffix} chars to given result 1377 * {@code container}. Updates {@code fastPathData.lastFreeIndex} 1378 * accordingly. 1379 * 1380 * @param suffix The suffix characters to append to result. 1381 * @param len The number of chars to append. 1382 * @param container Char array container which to append the suffix 1383 */ 1384 private void appendSuffix(char[] suffix, 1385 int len, 1386 char[] container) { 1387 1388 int startIndex = fastPathData.lastFreeIndex; 1389 1390 // If suffix to append is only 1 char long, just assigns this char. 1391 // If suffix is less or equal 4, we use a dedicated algorithm that 1392 // has shown to run faster than System.arraycopy. 1393 // If more than 4, we use System.arraycopy. 1394 if (len == 1) 1395 container[startIndex] = suffix[0]; 1396 else if (len <= 4) { 1397 int dstLower = startIndex; 1398 int dstUpper = dstLower + len - 1; 1399 int srcUpper = len - 1; 1400 container[dstLower] = suffix[0]; 1401 container[dstUpper] = suffix[srcUpper]; 1402 1403 if (len > 2) 1404 container[++dstLower] = suffix[1]; 1405 if (len == 4) 1406 container[--dstUpper] = suffix[2]; 1407 } else 1408 System.arraycopy(suffix, 0, container, startIndex, len); 1409 1410 fastPathData.lastFreeIndex += len; 1411 } 1412 1413 /** 1414 * Converts digit chars from {@code digitsBuffer} to current locale. 1415 * 1416 * Must be called before adding affixes since we refer to 1417 * {@code fastPathData.firstUsedIndex} and {@code fastPathData.lastFreeIndex}, 1418 * and do not support affixes (for speed reason). 1419 * 1420 * We loop backward starting from last used index in {@code fastPathData}. 1421 * 1422 * @param digitsBuffer The char array container where the digits are stored. 1423 */ 1424 private void localizeDigits(char[] digitsBuffer) { 1425 1426 // We will localize only the digits, using the groupingSize, 1427 // and taking into account fractional part. 1428 1429 // First take into account fractional part. 1430 int digitsCounter = 1431 fastPathData.lastFreeIndex - fastPathData.fractionalFirstIndex; 1432 1433 // The case when there is no fractional digits. 1434 if (digitsCounter < 0) 1435 digitsCounter = groupingSize; 1436 1437 // Only the digits remains to localize. 1438 for (int cursor = fastPathData.lastFreeIndex - 1; 1439 cursor >= fastPathData.firstUsedIndex; 1440 cursor--) { 1441 if (digitsCounter != 0) { 1442 // This is a digit char, we must localize it. 1443 digitsBuffer[cursor] += fastPathData.zeroDelta; 1444 digitsCounter--; 1445 } else { 1446 // Decimal separator or grouping char. Reinit counter only. 1447 digitsCounter = groupingSize; 1448 } 1449 } 1450 } 1451 1452 /** 1453 * This is the main entry point for the fast-path format algorithm. 1454 * 1455 * At this point we are sure to be in the expected conditions to run it. 1456 * This algorithm builds the formatted result and puts it in the dedicated 1457 * {@code fastPathData.fastPathContainer}. 1458 * 1459 * @param d the double value to be formatted. 1460 * @param negative Flag precising if {@code d} is negative. 1461 */ 1462 private void fastDoubleFormat(double d, 1463 boolean negative) { 1464 1465 char[] container = fastPathData.fastPathContainer; 1466 1467 /* 1468 * The principle of the algorithm is to : 1469 * - Break the passed double into its integral and fractional parts 1470 * converted into integers. 1471 * - Then decide if rounding up must be applied or not by following 1472 * the half-even rounding rule, first using approximated scaled 1473 * fractional part. 1474 * - For the difficult cases (approximated scaled fractional part 1475 * being exactly 0.5d), we refine the rounding decision by calling 1476 * exactRoundUp utility method that both calculates the exact roundoff 1477 * on the approximation and takes correct rounding decision. 1478 * - We round-up the fractional part if needed, possibly propagating the 1479 * rounding to integral part if we meet a "all-nine" case for the 1480 * scaled fractional part. 1481 * - We then collect digits from the resulting integral and fractional 1482 * parts, also setting the required grouping chars on the fly. 1483 * - Then we localize the collected digits if needed, and 1484 * - Finally prepend/append prefix/suffix if any is needed. 1485 */ 1486 1487 // Exact integral part of d. 1488 int integralPartAsInt = (int) d; 1489 1490 // Exact fractional part of d (since we subtract it's integral part). 1491 double exactFractionalPart = d - (double) integralPartAsInt; 1492 1493 // Approximated scaled fractional part of d (due to multiplication). 1494 double scaledFractional = 1495 exactFractionalPart * fastPathData.fractionalScaleFactor; 1496 1497 // Exact integral part of scaled fractional above. 1498 int fractionalPartAsInt = (int) scaledFractional; 1499 1500 // Exact fractional part of scaled fractional above. 1501 scaledFractional = scaledFractional - (double) fractionalPartAsInt; 1502 1503 // Only when scaledFractional is exactly 0.5d do we have to do exact 1504 // calculations and take fine-grained rounding decision, since 1505 // approximated results above may lead to incorrect decision. 1506 // Otherwise comparing against 0.5d (strictly greater or less) is ok. 1507 boolean roundItUp = false; 1508 if (scaledFractional >= 0.5d) { 1509 if (scaledFractional == 0.5d) 1510 // Rounding need fine-grained decision. 1511 roundItUp = exactRoundUp(exactFractionalPart, fractionalPartAsInt); 1512 else 1513 roundItUp = true; 1514 1515 if (roundItUp) { 1516 // Rounds up both fractional part (and also integral if needed). 1517 if (fractionalPartAsInt < fastPathData.fractionalMaxIntBound) { 1518 fractionalPartAsInt++; 1519 } else { 1520 // Propagates rounding to integral part since "all nines" case. 1521 fractionalPartAsInt = 0; 1522 integralPartAsInt++; 1523 } 1524 } 1525 } 1526 1527 // Collecting digits. 1528 collectFractionalDigits(fractionalPartAsInt, container, 1529 fastPathData.fractionalFirstIndex); 1530 collectIntegralDigits(integralPartAsInt, container, 1531 fastPathData.integralLastIndex); 1532 1533 // Localizing digits. 1534 if (fastPathData.zeroDelta != 0) 1535 localizeDigits(container); 1536 1537 // Adding prefix and suffix. 1538 if (negative) { 1539 if (fastPathData.negativeAffixesRequired) 1540 addAffixes(container, 1541 fastPathData.charsNegativePrefix, 1542 fastPathData.charsNegativeSuffix); 1543 } else if (fastPathData.positiveAffixesRequired) 1544 addAffixes(container, 1545 fastPathData.charsPositivePrefix, 1546 fastPathData.charsPositiveSuffix); 1547 } 1548 1549 /** 1550 * A fast-path shortcut of format(double) to be called by NumberFormat, or by 1551 * format(double, ...) public methods. 1552 * 1553 * If instance can be applied fast-path and passed double is not NaN or 1554 * Infinity, is in the integer range, we call {@code fastDoubleFormat} 1555 * after changing {@code d} to its positive value if necessary. 1556 * 1557 * Otherwise returns null by convention since fast-path can't be exercized. 1558 * 1559 * @param d The double value to be formatted 1560 * 1561 * @return the formatted result for {@code d} as a string. 1562 */ 1563 String fastFormat(double d) { 1564 // (Re-)Evaluates fast-path status if needed. 1565 if (fastPathCheckNeeded) 1566 checkAndSetFastPathStatus(); 1567 1568 if (!isFastPath ) 1569 // DecimalFormat instance is not in a fast-path state. 1570 return null; 1571 1572 if (!Double.isFinite(d)) 1573 // Should not use fast-path for Infinity and NaN. 1574 return null; 1575 1576 // Extracts and records sign of double value, possibly changing it 1577 // to a positive one, before calling fastDoubleFormat(). 1578 boolean negative = false; 1579 if (d < 0.0d) { 1580 negative = true; 1581 d = -d; 1582 } else if (d == 0.0d) { 1583 negative = (Math.copySign(1.0d, d) == -1.0d); 1584 d = +0.0d; 1585 } 1586 1587 if (d > MAX_INT_AS_DOUBLE) 1588 // Filters out values that are outside expected fast-path range 1589 return null; 1590 else 1591 fastDoubleFormat(d, negative); 1592 1593 // Returns a new string from updated fastPathContainer. 1594 return new String(fastPathData.fastPathContainer, 1595 fastPathData.firstUsedIndex, 1596 fastPathData.lastFreeIndex - fastPathData.firstUsedIndex); 1597 1598 } 1599 1600 // ======== End fast-path formating logic for double ========================= 1601 1602 /** 1603 * Complete the formatting of a finite number. On entry, the digitList must 1604 * be filled in with the correct digits. 1605 */ 1606 private StringBuffer subformat(StringBuffer result, FieldDelegate delegate, 1607 boolean isNegative, boolean isInteger, 1608 int maxIntDigits, int minIntDigits, 1609 int maxFraDigits, int minFraDigits) { 1610 // NOTE: This isn't required anymore because DigitList takes care of this. 1611 // 1612 // // The negative of the exponent represents the number of leading 1613 // // zeros between the decimal and the first non-zero digit, for 1614 // // a value < 0.1 (e.g., for 0.00123, -fExponent == 2). If this 1615 // // is more than the maximum fraction digits, then we have an underflow 1616 // // for the printed representation. We recognize this here and set 1617 // // the DigitList representation to zero in this situation. 1618 // 1619 // if (-digitList.decimalAt >= getMaximumFractionDigits()) 1620 // { 1621 // digitList.count = 0; 1622 // } 1623 1624 char zero = symbols.getZeroDigit(); 1625 int zeroDelta = zero - '0'; // '0' is the DigitList representation of zero 1626 char grouping = symbols.getGroupingSeparator(); 1627 char decimal = isCurrencyFormat ? 1628 symbols.getMonetaryDecimalSeparator() : 1629 symbols.getDecimalSeparator(); 1630 1631 /* Per bug 4147706, DecimalFormat must respect the sign of numbers which 1632 * format as zero. This allows sensible computations and preserves 1633 * relations such as signum(1/x) = signum(x), where x is +Infinity or 1634 * -Infinity. Prior to this fix, we always formatted zero values as if 1635 * they were positive. Liu 7/6/98. 1636 */ 1637 if (digitList.isZero()) { 1638 digitList.decimalAt = 0; // Normalize 1639 } 1640 1641 if (isNegative) { 1642 append(result, negativePrefix, delegate, 1643 getNegativePrefixFieldPositions(), Field.SIGN); 1644 } else { 1645 append(result, positivePrefix, delegate, 1646 getPositivePrefixFieldPositions(), Field.SIGN); 1647 } 1648 1649 if (useExponentialNotation) { 1650 int iFieldStart = result.length(); 1651 int iFieldEnd = -1; 1652 int fFieldStart = -1; 1653 1654 // Minimum integer digits are handled in exponential format by 1655 // adjusting the exponent. For example, 0.01234 with 3 minimum 1656 // integer digits is "123.4E-4". 1657 1658 // Maximum integer digits are interpreted as indicating the 1659 // repeating range. This is useful for engineering notation, in 1660 // which the exponent is restricted to a multiple of 3. For 1661 // example, 0.01234 with 3 maximum integer digits is "12.34e-3". 1662 // If maximum integer digits are > 1 and are larger than 1663 // minimum integer digits, then minimum integer digits are 1664 // ignored. 1665 int exponent = digitList.decimalAt; 1666 int repeat = maxIntDigits; 1667 int minimumIntegerDigits = minIntDigits; 1668 if (repeat > 1 && repeat > minIntDigits) { 1669 // A repeating range is defined; adjust to it as follows. 1670 // If repeat == 3, we have 6,5,4=>3; 3,2,1=>0; 0,-1,-2=>-3; 1671 // -3,-4,-5=>-6, etc. This takes into account that the 1672 // exponent we have here is off by one from what we expect; 1673 // it is for the format 0.MMMMMx10^n. 1674 if (exponent >= 1) { 1675 exponent = ((exponent - 1) / repeat) * repeat; 1676 } else { 1677 // integer division rounds towards 0 1678 exponent = ((exponent - repeat) / repeat) * repeat; 1679 } 1680 minimumIntegerDigits = 1; 1681 } else { 1682 // No repeating range is defined; use minimum integer digits. 1683 exponent -= minimumIntegerDigits; 1684 } 1685 1686 // We now output a minimum number of digits, and more if there 1687 // are more digits, up to the maximum number of digits. We 1688 // place the decimal point after the "integer" digits, which 1689 // are the first (decimalAt - exponent) digits. 1690 int minimumDigits = minIntDigits + minFraDigits; 1691 if (minimumDigits < 0) { // overflow? 1692 minimumDigits = Integer.MAX_VALUE; 1693 } 1694 1695 // The number of integer digits is handled specially if the number 1696 // is zero, since then there may be no digits. 1697 int integerDigits = digitList.isZero() ? minimumIntegerDigits : 1698 digitList.decimalAt - exponent; 1699 if (minimumDigits < integerDigits) { 1700 minimumDigits = integerDigits; 1701 } 1702 int totalDigits = digitList.count; 1703 if (minimumDigits > totalDigits) { 1704 totalDigits = minimumDigits; 1705 } 1706 boolean addedDecimalSeparator = false; 1707 1708 for (int i=0; i<totalDigits; ++i) { 1709 if (i == integerDigits) { 1710 // Record field information for caller. 1711 iFieldEnd = result.length(); 1712 1713 result.append(decimal); 1714 addedDecimalSeparator = true; 1715 1716 // Record field information for caller. 1717 fFieldStart = result.length(); 1718 } 1719 result.append((i < digitList.count) ? 1720 (char)(digitList.digits[i] + zeroDelta) : 1721 zero); 1722 } 1723 1724 if (decimalSeparatorAlwaysShown && totalDigits == integerDigits) { 1725 // Record field information for caller. 1726 iFieldEnd = result.length(); 1727 1728 result.append(decimal); 1729 addedDecimalSeparator = true; 1730 1731 // Record field information for caller. 1732 fFieldStart = result.length(); 1733 } 1734 1735 // Record field information 1736 if (iFieldEnd == -1) { 1737 iFieldEnd = result.length(); 1738 } 1739 delegate.formatted(INTEGER_FIELD, Field.INTEGER, Field.INTEGER, 1740 iFieldStart, iFieldEnd, result); 1741 if (addedDecimalSeparator) { 1742 delegate.formatted(Field.DECIMAL_SEPARATOR, 1743 Field.DECIMAL_SEPARATOR, 1744 iFieldEnd, fFieldStart, result); 1745 } 1746 if (fFieldStart == -1) { 1747 fFieldStart = result.length(); 1748 } 1749 delegate.formatted(FRACTION_FIELD, Field.FRACTION, Field.FRACTION, 1750 fFieldStart, result.length(), result); 1751 1752 // The exponent is output using the pattern-specified minimum 1753 // exponent digits. There is no maximum limit to the exponent 1754 // digits, since truncating the exponent would result in an 1755 // unacceptable inaccuracy. 1756 int fieldStart = result.length(); 1757 1758 result.append(symbols.getExponentSeparator()); 1759 1760 delegate.formatted(Field.EXPONENT_SYMBOL, Field.EXPONENT_SYMBOL, 1761 fieldStart, result.length(), result); 1762 1763 // For zero values, we force the exponent to zero. We 1764 // must do this here, and not earlier, because the value 1765 // is used to determine integer digit count above. 1766 if (digitList.isZero()) { 1767 exponent = 0; 1768 } 1769 1770 boolean negativeExponent = exponent < 0; 1771 if (negativeExponent) { 1772 exponent = -exponent; 1773 fieldStart = result.length(); 1774 result.append(symbols.getMinusSign()); 1775 delegate.formatted(Field.EXPONENT_SIGN, Field.EXPONENT_SIGN, 1776 fieldStart, result.length(), result); 1777 } 1778 digitList.set(negativeExponent, exponent); 1779 1780 int eFieldStart = result.length(); 1781 1782 for (int i=digitList.decimalAt; i<minExponentDigits; ++i) { 1783 result.append(zero); 1784 } 1785 for (int i=0; i<digitList.decimalAt; ++i) { 1786 result.append((i < digitList.count) ? 1787 (char)(digitList.digits[i] + zeroDelta) : zero); 1788 } 1789 delegate.formatted(Field.EXPONENT, Field.EXPONENT, eFieldStart, 1790 result.length(), result); 1791 } else { 1792 int iFieldStart = result.length(); 1793 1794 // Output the integer portion. Here 'count' is the total 1795 // number of integer digits we will display, including both 1796 // leading zeros required to satisfy getMinimumIntegerDigits, 1797 // and actual digits present in the number. 1798 int count = minIntDigits; 1799 int digitIndex = 0; // Index into digitList.fDigits[] 1800 if (digitList.decimalAt > 0 && count < digitList.decimalAt) { 1801 count = digitList.decimalAt; 1802 } 1803 1804 // Handle the case where getMaximumIntegerDigits() is smaller 1805 // than the real number of integer digits. If this is so, we 1806 // output the least significant max integer digits. For example, 1807 // the value 1997 printed with 2 max integer digits is just "97". 1808 if (count > maxIntDigits) { 1809 count = maxIntDigits; 1810 digitIndex = digitList.decimalAt - count; 1811 } 1812 1813 int sizeBeforeIntegerPart = result.length(); 1814 for (int i=count-1; i>=0; --i) { 1815 if (i < digitList.decimalAt && digitIndex < digitList.count) { 1816 // Output a real digit 1817 result.append((char)(digitList.digits[digitIndex++] + zeroDelta)); 1818 } else { 1819 // Output a leading zero 1820 result.append(zero); 1821 } 1822 1823 // Output grouping separator if necessary. Don't output a 1824 // grouping separator if i==0 though; that's at the end of 1825 // the integer part. 1826 if (isGroupingUsed() && i>0 && (groupingSize != 0) && 1827 (i % groupingSize == 0)) { 1828 int gStart = result.length(); 1829 result.append(grouping); 1830 delegate.formatted(Field.GROUPING_SEPARATOR, 1831 Field.GROUPING_SEPARATOR, gStart, 1832 result.length(), result); 1833 } 1834 } 1835 1836 // Determine whether or not there are any printable fractional 1837 // digits. If we've used up the digits we know there aren't. 1838 boolean fractionPresent = (minFraDigits > 0) || 1839 (!isInteger && digitIndex < digitList.count); 1840 1841 // If there is no fraction present, and we haven't printed any 1842 // integer digits, then print a zero. Otherwise we won't print 1843 // _any_ digits, and we won't be able to parse this string. 1844 if (!fractionPresent && result.length() == sizeBeforeIntegerPart) { 1845 result.append(zero); 1846 } 1847 1848 delegate.formatted(INTEGER_FIELD, Field.INTEGER, Field.INTEGER, 1849 iFieldStart, result.length(), result); 1850 1851 // Output the decimal separator if we always do so. 1852 int sStart = result.length(); 1853 if (decimalSeparatorAlwaysShown || fractionPresent) { 1854 result.append(decimal); 1855 } 1856 1857 if (sStart != result.length()) { 1858 delegate.formatted(Field.DECIMAL_SEPARATOR, 1859 Field.DECIMAL_SEPARATOR, 1860 sStart, result.length(), result); 1861 } 1862 int fFieldStart = result.length(); 1863 1864 for (int i=0; i < maxFraDigits; ++i) { 1865 // Here is where we escape from the loop. We escape if we've 1866 // output the maximum fraction digits (specified in the for 1867 // expression above). 1868 // We also stop when we've output the minimum digits and either: 1869 // we have an integer, so there is no fractional stuff to 1870 // display, or we're out of significant digits. 1871 if (i >= minFraDigits && 1872 (isInteger || digitIndex >= digitList.count)) { 1873 break; 1874 } 1875 1876 // Output leading fractional zeros. These are zeros that come 1877 // after the decimal but before any significant digits. These 1878 // are only output if abs(number being formatted) < 1.0. 1879 if (-1-i > (digitList.decimalAt-1)) { 1880 result.append(zero); 1881 continue; 1882 } 1883 1884 // Output a digit, if we have any precision left, or a 1885 // zero if we don't. We don't want to output noise digits. 1886 if (!isInteger && digitIndex < digitList.count) { 1887 result.append((char)(digitList.digits[digitIndex++] + zeroDelta)); 1888 } else { 1889 result.append(zero); 1890 } 1891 } 1892 1893 // Record field information for caller. 1894 delegate.formatted(FRACTION_FIELD, Field.FRACTION, Field.FRACTION, 1895 fFieldStart, result.length(), result); 1896 } 1897 1898 if (isNegative) { 1899 append(result, negativeSuffix, delegate, 1900 getNegativeSuffixFieldPositions(), Field.SIGN); 1901 } else { 1902 append(result, positiveSuffix, delegate, 1903 getPositiveSuffixFieldPositions(), Field.SIGN); 1904 } 1905 1906 return result; 1907 } 1908 1909 /** 1910 * Appends the String <code>string</code> to <code>result</code>. 1911 * <code>delegate</code> is notified of all the 1912 * <code>FieldPosition</code>s in <code>positions</code>. 1913 * <p> 1914 * If one of the <code>FieldPosition</code>s in <code>positions</code> 1915 * identifies a <code>SIGN</code> attribute, it is mapped to 1916 * <code>signAttribute</code>. This is used 1917 * to map the <code>SIGN</code> attribute to the <code>EXPONENT</code> 1918 * attribute as necessary. 1919 * <p> 1920 * This is used by <code>subformat</code> to add the prefix/suffix. 1921 */ 1922 private void append(StringBuffer result, String string, 1923 FieldDelegate delegate, 1924 FieldPosition[] positions, 1925 Format.Field signAttribute) { 1926 int start = result.length(); 1927 1928 if (string.length() > 0) { 1929 result.append(string); 1930 for (int counter = 0, max = positions.length; counter < max; 1931 counter++) { 1932 FieldPosition fp = positions[counter]; 1933 Format.Field attribute = fp.getFieldAttribute(); 1934 1935 if (attribute == Field.SIGN) { 1936 attribute = signAttribute; 1937 } 1938 delegate.formatted(attribute, attribute, 1939 start + fp.getBeginIndex(), 1940 start + fp.getEndIndex(), result); 1941 } 1942 } 1943 } 1944 1945 /** 1946 * Parses text from a string to produce a <code>Number</code>. 1947 * <p> 1948 * The method attempts to parse text starting at the index given by 1949 * <code>pos</code>. 1950 * If parsing succeeds, then the index of <code>pos</code> is updated 1951 * to the index after the last character used (parsing does not necessarily 1952 * use all characters up to the end of the string), and the parsed 1953 * number is returned. The updated <code>pos</code> can be used to 1954 * indicate the starting point for the next call to this method. 1955 * If an error occurs, then the index of <code>pos</code> is not 1956 * changed, the error index of <code>pos</code> is set to the index of 1957 * the character where the error occurred, and null is returned. 1958 * <p> 1959 * The subclass returned depends on the value of {@link #isParseBigDecimal} 1960 * as well as on the string being parsed. 1961 * <ul> 1962 * <li>If <code>isParseBigDecimal()</code> is false (the default), 1963 * most integer values are returned as <code>Long</code> 1964 * objects, no matter how they are written: <code>"17"</code> and 1965 * <code>"17.000"</code> both parse to <code>Long(17)</code>. 1966 * Values that cannot fit into a <code>Long</code> are returned as 1967 * <code>Double</code>s. This includes values with a fractional part, 1968 * infinite values, <code>NaN</code>, and the value -0.0. 1969 * <code>DecimalFormat</code> does <em>not</em> decide whether to 1970 * return a <code>Double</code> or a <code>Long</code> based on the 1971 * presence of a decimal separator in the source string. Doing so 1972 * would prevent integers that overflow the mantissa of a double, 1973 * such as <code>"-9,223,372,036,854,775,808.00"</code>, from being 1974 * parsed accurately. 1975 * <p> 1976 * Callers may use the <code>Number</code> methods 1977 * <code>doubleValue</code>, <code>longValue</code>, etc., to obtain 1978 * the type they want. 1979 * <li>If <code>isParseBigDecimal()</code> is true, values are returned 1980 * as <code>BigDecimal</code> objects. The values are the ones 1981 * constructed by {@link java.math.BigDecimal#BigDecimal(String)} 1982 * for corresponding strings in locale-independent format. The 1983 * special cases negative and positive infinity and NaN are returned 1984 * as <code>Double</code> instances holding the values of the 1985 * corresponding <code>Double</code> constants. 1986 * </ul> 1987 * <p> 1988 * <code>DecimalFormat</code> parses all Unicode characters that represent 1989 * decimal digits, as defined by <code>Character.digit()</code>. In 1990 * addition, <code>DecimalFormat</code> also recognizes as digits the ten 1991 * consecutive characters starting with the localized zero digit defined in 1992 * the <code>DecimalFormatSymbols</code> object. 1993 * 1994 * @param text the string to be parsed 1995 * @param pos A <code>ParsePosition</code> object with index and error 1996 * index information as described above. 1997 * @return the parsed value, or <code>null</code> if the parse fails 1998 * @exception NullPointerException if <code>text</code> or 1999 * <code>pos</code> is null. 2000 */ 2001 @Override 2002 public Number parse(String text, ParsePosition pos) { 2003 // special case NaN 2004 if (text.regionMatches(pos.index, symbols.getNaN(), 0, symbols.getNaN().length())) { 2005 pos.index = pos.index + symbols.getNaN().length(); 2006 return new Double(Double.NaN); 2007 } 2008 2009 boolean[] status = new boolean[STATUS_LENGTH]; 2010 if (!subparse(text, pos, positivePrefix, negativePrefix, digitList, false, status)) { 2011 return null; 2012 } 2013 2014 // special case INFINITY 2015 if (status[STATUS_INFINITE]) { 2016 if (status[STATUS_POSITIVE] == (multiplier >= 0)) { 2017 return new Double(Double.POSITIVE_INFINITY); 2018 } else { 2019 return new Double(Double.NEGATIVE_INFINITY); 2020 } 2021 } 2022 2023 if (multiplier == 0) { 2024 if (digitList.isZero()) { 2025 return new Double(Double.NaN); 2026 } else if (status[STATUS_POSITIVE]) { 2027 return new Double(Double.POSITIVE_INFINITY); 2028 } else { 2029 return new Double(Double.NEGATIVE_INFINITY); 2030 } 2031 } 2032 2033 if (isParseBigDecimal()) { 2034 BigDecimal bigDecimalResult = digitList.getBigDecimal(); 2035 2036 if (multiplier != 1) { 2037 try { 2038 bigDecimalResult = bigDecimalResult.divide(getBigDecimalMultiplier()); 2039 } 2040 catch (ArithmeticException e) { // non-terminating decimal expansion 2041 bigDecimalResult = bigDecimalResult.divide(getBigDecimalMultiplier(), roundingMode); 2042 } 2043 } 2044 2045 if (!status[STATUS_POSITIVE]) { 2046 bigDecimalResult = bigDecimalResult.negate(); 2047 } 2048 return bigDecimalResult; 2049 } else { 2050 boolean gotDouble = true; 2051 boolean gotLongMinimum = false; 2052 double doubleResult = 0.0; 2053 long longResult = 0; 2054 2055 // Finally, have DigitList parse the digits into a value. 2056 if (digitList.fitsIntoLong(status[STATUS_POSITIVE], isParseIntegerOnly())) { 2057 gotDouble = false; 2058 longResult = digitList.getLong(); 2059 if (longResult < 0) { // got Long.MIN_VALUE 2060 gotLongMinimum = true; 2061 } 2062 } else { 2063 doubleResult = digitList.getDouble(); 2064 } 2065 2066 // Divide by multiplier. We have to be careful here not to do 2067 // unneeded conversions between double and long. 2068 if (multiplier != 1) { 2069 if (gotDouble) { 2070 doubleResult /= multiplier; 2071 } else { 2072 // Avoid converting to double if we can 2073 if (longResult % multiplier == 0) { 2074 longResult /= multiplier; 2075 } else { 2076 doubleResult = ((double)longResult) / multiplier; 2077 gotDouble = true; 2078 } 2079 } 2080 } 2081 2082 if (!status[STATUS_POSITIVE] && !gotLongMinimum) { 2083 doubleResult = -doubleResult; 2084 longResult = -longResult; 2085 } 2086 2087 // At this point, if we divided the result by the multiplier, the 2088 // result may fit into a long. We check for this case and return 2089 // a long if possible. 2090 // We must do this AFTER applying the negative (if appropriate) 2091 // in order to handle the case of LONG_MIN; otherwise, if we do 2092 // this with a positive value -LONG_MIN, the double is > 0, but 2093 // the long is < 0. We also must retain a double in the case of 2094 // -0.0, which will compare as == to a long 0 cast to a double 2095 // (bug 4162852). 2096 if (multiplier != 1 && gotDouble) { 2097 longResult = (long)doubleResult; 2098 gotDouble = ((doubleResult != (double)longResult) || 2099 (doubleResult == 0.0 && 1/doubleResult < 0.0)) && 2100 !isParseIntegerOnly(); 2101 } 2102 2103 return gotDouble ? 2104 (Number)new Double(doubleResult) : (Number)new Long(longResult); 2105 } 2106 } 2107 2108 /** 2109 * Return a BigInteger multiplier. 2110 */ 2111 private BigInteger getBigIntegerMultiplier() { 2112 if (bigIntegerMultiplier == null) { 2113 bigIntegerMultiplier = BigInteger.valueOf(multiplier); 2114 } 2115 return bigIntegerMultiplier; 2116 } 2117 private transient BigInteger bigIntegerMultiplier; 2118 2119 /** 2120 * Return a BigDecimal multiplier. 2121 */ 2122 private BigDecimal getBigDecimalMultiplier() { 2123 if (bigDecimalMultiplier == null) { 2124 bigDecimalMultiplier = new BigDecimal(multiplier); 2125 } 2126 return bigDecimalMultiplier; 2127 } 2128 private transient BigDecimal bigDecimalMultiplier; 2129 2130 private static final int STATUS_INFINITE = 0; 2131 private static final int STATUS_POSITIVE = 1; 2132 private static final int STATUS_LENGTH = 2; 2133 2134 /** 2135 * Parse the given text into a number. The text is parsed beginning at 2136 * parsePosition, until an unparseable character is seen. 2137 * @param text The string to parse. 2138 * @param parsePosition The position at which to being parsing. Upon 2139 * return, the first unparseable character. 2140 * @param digits The DigitList to set to the parsed value. 2141 * @param isExponent If true, parse an exponent. This means no 2142 * infinite values and integer only. 2143 * @param status Upon return contains boolean status flags indicating 2144 * whether the value was infinite and whether it was positive. 2145 */ 2146 private final boolean subparse(String text, ParsePosition parsePosition, 2147 String positivePrefix, String negativePrefix, 2148 DigitList digits, boolean isExponent, 2149 boolean status[]) { 2150 int position = parsePosition.index; 2151 int oldStart = parsePosition.index; 2152 int backup; 2153 boolean gotPositive, gotNegative; 2154 2155 // check for positivePrefix; take longest 2156 gotPositive = text.regionMatches(position, positivePrefix, 0, 2157 positivePrefix.length()); 2158 gotNegative = text.regionMatches(position, negativePrefix, 0, 2159 negativePrefix.length()); 2160 2161 if (gotPositive && gotNegative) { 2162 if (positivePrefix.length() > negativePrefix.length()) { 2163 gotNegative = false; 2164 } else if (positivePrefix.length() < negativePrefix.length()) { 2165 gotPositive = false; 2166 } 2167 } 2168 2169 if (gotPositive) { 2170 position += positivePrefix.length(); 2171 } else if (gotNegative) { 2172 position += negativePrefix.length(); 2173 } else { 2174 parsePosition.errorIndex = position; 2175 return false; 2176 } 2177 2178 // process digits or Inf, find decimal position 2179 status[STATUS_INFINITE] = false; 2180 if (!isExponent && text.regionMatches(position,symbols.getInfinity(),0, 2181 symbols.getInfinity().length())) { 2182 position += symbols.getInfinity().length(); 2183 status[STATUS_INFINITE] = true; 2184 } else { 2185 // We now have a string of digits, possibly with grouping symbols, 2186 // and decimal points. We want to process these into a DigitList. 2187 // We don't want to put a bunch of leading zeros into the DigitList 2188 // though, so we keep track of the location of the decimal point, 2189 // put only significant digits into the DigitList, and adjust the 2190 // exponent as needed. 2191 2192 digits.decimalAt = digits.count = 0; 2193 char zero = symbols.getZeroDigit(); 2194 char decimal = isCurrencyFormat ? 2195 symbols.getMonetaryDecimalSeparator() : 2196 symbols.getDecimalSeparator(); 2197 char grouping = symbols.getGroupingSeparator(); 2198 String exponentString = symbols.getExponentSeparator(); 2199 boolean sawDecimal = false; 2200 boolean sawExponent = false; 2201 boolean sawDigit = false; 2202 int exponent = 0; // Set to the exponent value, if any 2203 2204 // We have to track digitCount ourselves, because digits.count will 2205 // pin when the maximum allowable digits is reached. 2206 int digitCount = 0; 2207 2208 backup = -1; 2209 for (; position < text.length(); ++position) { 2210 char ch = text.charAt(position); 2211 2212 /* We recognize all digit ranges, not only the Latin digit range 2213 * '0'..'9'. We do so by using the Character.digit() method, 2214 * which converts a valid Unicode digit to the range 0..9. 2215 * 2216 * The character 'ch' may be a digit. If so, place its value 2217 * from 0 to 9 in 'digit'. First try using the locale digit, 2218 * which may or MAY NOT be a standard Unicode digit range. If 2219 * this fails, try using the standard Unicode digit ranges by 2220 * calling Character.digit(). If this also fails, digit will 2221 * have a value outside the range 0..9. 2222 */ 2223 int digit = ch - zero; 2224 if (digit < 0 || digit > 9) { 2225 digit = Character.digit(ch, 10); 2226 } 2227 2228 if (digit == 0) { 2229 // Cancel out backup setting (see grouping handler below) 2230 backup = -1; // Do this BEFORE continue statement below!!! 2231 sawDigit = true; 2232 2233 // Handle leading zeros 2234 if (digits.count == 0) { 2235 // Ignore leading zeros in integer part of number. 2236 if (!sawDecimal) { 2237 continue; 2238 } 2239 2240 // If we have seen the decimal, but no significant 2241 // digits yet, then we account for leading zeros by 2242 // decrementing the digits.decimalAt into negative 2243 // values. 2244 --digits.decimalAt; 2245 } else { 2246 ++digitCount; 2247 digits.append((char)(digit + '0')); 2248 } 2249 } else if (digit > 0 && digit <= 9) { // [sic] digit==0 handled above 2250 sawDigit = true; 2251 ++digitCount; 2252 digits.append((char)(digit + '0')); 2253 2254 // Cancel out backup setting (see grouping handler below) 2255 backup = -1; 2256 } else if (!isExponent && ch == decimal) { 2257 // If we're only parsing integers, or if we ALREADY saw the 2258 // decimal, then don't parse this one. 2259 if (isParseIntegerOnly() || sawDecimal) { 2260 break; 2261 } 2262 digits.decimalAt = digitCount; // Not digits.count! 2263 sawDecimal = true; 2264 } else if (!isExponent && ch == grouping && isGroupingUsed()) { 2265 if (sawDecimal) { 2266 break; 2267 } 2268 // Ignore grouping characters, if we are using them, but 2269 // require that they be followed by a digit. Otherwise 2270 // we backup and reprocess them. 2271 backup = position; 2272 } else if (!isExponent && text.regionMatches(position, exponentString, 0, exponentString.length()) 2273 && !sawExponent) { 2274 // Process the exponent by recursively calling this method. 2275 ParsePosition pos = new ParsePosition(position + exponentString.length()); 2276 boolean[] stat = new boolean[STATUS_LENGTH]; 2277 DigitList exponentDigits = new DigitList(); 2278 2279 if (subparse(text, pos, "", Character.toString(symbols.getMinusSign()), exponentDigits, true, stat) && 2280 exponentDigits.fitsIntoLong(stat[STATUS_POSITIVE], true)) { 2281 position = pos.index; // Advance past the exponent 2282 exponent = (int)exponentDigits.getLong(); 2283 if (!stat[STATUS_POSITIVE]) { 2284 exponent = -exponent; 2285 } 2286 sawExponent = true; 2287 } 2288 break; // Whether we fail or succeed, we exit this loop 2289 } else { 2290 break; 2291 } 2292 } 2293 2294 if (backup != -1) { 2295 position = backup; 2296 } 2297 2298 // If there was no decimal point we have an integer 2299 if (!sawDecimal) { 2300 digits.decimalAt = digitCount; // Not digits.count! 2301 } 2302 2303 // Adjust for exponent, if any 2304 digits.decimalAt += exponent; 2305 2306 // If none of the text string was recognized. For example, parse 2307 // "x" with pattern "#0.00" (return index and error index both 0) 2308 // parse "$" with pattern "$#0.00". (return index 0 and error 2309 // index 1). 2310 if (!sawDigit && digitCount == 0) { 2311 parsePosition.index = oldStart; 2312 parsePosition.errorIndex = oldStart; 2313 return false; 2314 } 2315 } 2316 2317 // check for suffix 2318 if (!isExponent) { 2319 if (gotPositive) { 2320 gotPositive = text.regionMatches(position,positiveSuffix,0, 2321 positiveSuffix.length()); 2322 } 2323 if (gotNegative) { 2324 gotNegative = text.regionMatches(position,negativeSuffix,0, 2325 negativeSuffix.length()); 2326 } 2327 2328 // if both match, take longest 2329 if (gotPositive && gotNegative) { 2330 if (positiveSuffix.length() > negativeSuffix.length()) { 2331 gotNegative = false; 2332 } else if (positiveSuffix.length() < negativeSuffix.length()) { 2333 gotPositive = false; 2334 } 2335 } 2336 2337 // fail if neither or both 2338 if (gotPositive == gotNegative) { 2339 parsePosition.errorIndex = position; 2340 return false; 2341 } 2342 2343 parsePosition.index = position + 2344 (gotPositive ? positiveSuffix.length() : negativeSuffix.length()); // mark success! 2345 } else { 2346 parsePosition.index = position; 2347 } 2348 2349 status[STATUS_POSITIVE] = gotPositive; 2350 if (parsePosition.index == oldStart) { 2351 parsePosition.errorIndex = position; 2352 return false; 2353 } 2354 return true; 2355 } 2356 2357 /** 2358 * Returns a copy of the decimal format symbols, which is generally not 2359 * changed by the programmer or user. 2360 * @return a copy of the desired DecimalFormatSymbols 2361 * @see java.text.DecimalFormatSymbols 2362 */ 2363 public DecimalFormatSymbols getDecimalFormatSymbols() { 2364 try { 2365 // don't allow multiple references 2366 return (DecimalFormatSymbols) symbols.clone(); 2367 } catch (Exception foo) { 2368 return null; // should never happen 2369 } 2370 } 2371 2372 2373 /** 2374 * Sets the decimal format symbols, which is generally not changed 2375 * by the programmer or user. 2376 * @param newSymbols desired DecimalFormatSymbols 2377 * @see java.text.DecimalFormatSymbols 2378 */ 2379 public void setDecimalFormatSymbols(DecimalFormatSymbols newSymbols) { 2380 try { 2381 // don't allow multiple references 2382 symbols = (DecimalFormatSymbols) newSymbols.clone(); 2383 expandAffixes(); 2384 fastPathCheckNeeded = true; 2385 } catch (Exception foo) { 2386 // should never happen 2387 } 2388 } 2389 2390 /** 2391 * Get the positive prefix. 2392 * <P>Examples: +123, $123, sFr123 2393 */ 2394 public String getPositivePrefix () { 2395 return positivePrefix; 2396 } 2397 2398 /** 2399 * Set the positive prefix. 2400 * <P>Examples: +123, $123, sFr123 2401 */ 2402 public void setPositivePrefix (String newValue) { 2403 positivePrefix = newValue; 2404 posPrefixPattern = null; 2405 positivePrefixFieldPositions = null; 2406 fastPathCheckNeeded = true; 2407 } 2408 2409 /** 2410 * Returns the FieldPositions of the fields in the prefix used for 2411 * positive numbers. This is not used if the user has explicitly set 2412 * a positive prefix via <code>setPositivePrefix</code>. This is 2413 * lazily created. 2414 * 2415 * @return FieldPositions in positive prefix 2416 */ 2417 private FieldPosition[] getPositivePrefixFieldPositions() { 2418 if (positivePrefixFieldPositions == null) { 2419 if (posPrefixPattern != null) { 2420 positivePrefixFieldPositions = expandAffix(posPrefixPattern); 2421 } else { 2422 positivePrefixFieldPositions = EmptyFieldPositionArray; 2423 } 2424 } 2425 return positivePrefixFieldPositions; 2426 } 2427 2428 /** 2429 * Get the negative prefix. 2430 * <P>Examples: -123, ($123) (with negative suffix), sFr-123 2431 */ 2432 public String getNegativePrefix () { 2433 return negativePrefix; 2434 } 2435 2436 /** 2437 * Set the negative prefix. 2438 * <P>Examples: -123, ($123) (with negative suffix), sFr-123 2439 */ 2440 public void setNegativePrefix (String newValue) { 2441 negativePrefix = newValue; 2442 negPrefixPattern = null; 2443 fastPathCheckNeeded = true; 2444 } 2445 2446 /** 2447 * Returns the FieldPositions of the fields in the prefix used for 2448 * negative numbers. This is not used if the user has explicitly set 2449 * a negative prefix via <code>setNegativePrefix</code>. This is 2450 * lazily created. 2451 * 2452 * @return FieldPositions in positive prefix 2453 */ 2454 private FieldPosition[] getNegativePrefixFieldPositions() { 2455 if (negativePrefixFieldPositions == null) { 2456 if (negPrefixPattern != null) { 2457 negativePrefixFieldPositions = expandAffix(negPrefixPattern); 2458 } else { 2459 negativePrefixFieldPositions = EmptyFieldPositionArray; 2460 } 2461 } 2462 return negativePrefixFieldPositions; 2463 } 2464 2465 /** 2466 * Get the positive suffix. 2467 * <P>Example: 123% 2468 */ 2469 public String getPositiveSuffix () { 2470 return positiveSuffix; 2471 } 2472 2473 /** 2474 * Set the positive suffix. 2475 * <P>Example: 123% 2476 */ 2477 public void setPositiveSuffix (String newValue) { 2478 positiveSuffix = newValue; 2479 posSuffixPattern = null; 2480 fastPathCheckNeeded = true; 2481 } 2482 2483 /** 2484 * Returns the FieldPositions of the fields in the suffix used for 2485 * positive numbers. This is not used if the user has explicitly set 2486 * a positive suffix via <code>setPositiveSuffix</code>. This is 2487 * lazily created. 2488 * 2489 * @return FieldPositions in positive prefix 2490 */ 2491 private FieldPosition[] getPositiveSuffixFieldPositions() { 2492 if (positiveSuffixFieldPositions == null) { 2493 if (posSuffixPattern != null) { 2494 positiveSuffixFieldPositions = expandAffix(posSuffixPattern); 2495 } else { 2496 positiveSuffixFieldPositions = EmptyFieldPositionArray; 2497 } 2498 } 2499 return positiveSuffixFieldPositions; 2500 } 2501 2502 /** 2503 * Get the negative suffix. 2504 * <P>Examples: -123%, ($123) (with positive suffixes) 2505 */ 2506 public String getNegativeSuffix () { 2507 return negativeSuffix; 2508 } 2509 2510 /** 2511 * Set the negative suffix. 2512 * <P>Examples: 123% 2513 */ 2514 public void setNegativeSuffix (String newValue) { 2515 negativeSuffix = newValue; 2516 negSuffixPattern = null; 2517 fastPathCheckNeeded = true; 2518 } 2519 2520 /** 2521 * Returns the FieldPositions of the fields in the suffix used for 2522 * negative numbers. This is not used if the user has explicitly set 2523 * a negative suffix via <code>setNegativeSuffix</code>. This is 2524 * lazily created. 2525 * 2526 * @return FieldPositions in positive prefix 2527 */ 2528 private FieldPosition[] getNegativeSuffixFieldPositions() { 2529 if (negativeSuffixFieldPositions == null) { 2530 if (negSuffixPattern != null) { 2531 negativeSuffixFieldPositions = expandAffix(negSuffixPattern); 2532 } else { 2533 negativeSuffixFieldPositions = EmptyFieldPositionArray; 2534 } 2535 } 2536 return negativeSuffixFieldPositions; 2537 } 2538 2539 /** 2540 * Gets the multiplier for use in percent, per mille, and similar 2541 * formats. 2542 * 2543 * @see #setMultiplier(int) 2544 */ 2545 public int getMultiplier () { 2546 return multiplier; 2547 } 2548 2549 /** 2550 * Sets the multiplier for use in percent, per mille, and similar 2551 * formats. 2552 * For a percent format, set the multiplier to 100 and the suffixes to 2553 * have '%' (for Arabic, use the Arabic percent sign). 2554 * For a per mille format, set the multiplier to 1000 and the suffixes to 2555 * have '\u2030'. 2556 * 2557 * <P>Example: with multiplier 100, 1.23 is formatted as "123", and 2558 * "123" is parsed into 1.23. 2559 * 2560 * @see #getMultiplier 2561 */ 2562 public void setMultiplier (int newValue) { 2563 multiplier = newValue; 2564 bigDecimalMultiplier = null; 2565 bigIntegerMultiplier = null; 2566 fastPathCheckNeeded = true; 2567 } 2568 2569 /** 2570 * {@inheritDoc} 2571 */ 2572 @Override 2573 public void setGroupingUsed(boolean newValue) { 2574 super.setGroupingUsed(newValue); 2575 fastPathCheckNeeded = true; 2576 } 2577 2578 /** 2579 * Return the grouping size. Grouping size is the number of digits between 2580 * grouping separators in the integer portion of a number. For example, 2581 * in the number "123,456.78", the grouping size is 3. 2582 * @see #setGroupingSize 2583 * @see java.text.NumberFormat#isGroupingUsed 2584 * @see java.text.DecimalFormatSymbols#getGroupingSeparator 2585 */ 2586 public int getGroupingSize () { 2587 return groupingSize; 2588 } 2589 2590 /** 2591 * Set the grouping size. Grouping size is the number of digits between 2592 * grouping separators in the integer portion of a number. For example, 2593 * in the number "123,456.78", the grouping size is 3. 2594 * <br> 2595 * The value passed in is converted to a byte, which may lose information. 2596 * @see #getGroupingSize 2597 * @see java.text.NumberFormat#setGroupingUsed 2598 * @see java.text.DecimalFormatSymbols#setGroupingSeparator 2599 */ 2600 public void setGroupingSize (int newValue) { 2601 groupingSize = (byte)newValue; 2602 fastPathCheckNeeded = true; 2603 } 2604 2605 /** 2606 * Allows you to get the behavior of the decimal separator with integers. 2607 * (The decimal separator will always appear with decimals.) 2608 * <P>Example: Decimal ON: 12345 -> 12345.; OFF: 12345 -> 12345 2609 */ 2610 public boolean isDecimalSeparatorAlwaysShown() { 2611 return decimalSeparatorAlwaysShown; 2612 } 2613 2614 /** 2615 * Allows you to set the behavior of the decimal separator with integers. 2616 * (The decimal separator will always appear with decimals.) 2617 * <P>Example: Decimal ON: 12345 -> 12345.; OFF: 12345 -> 12345 2618 */ 2619 public void setDecimalSeparatorAlwaysShown(boolean newValue) { 2620 decimalSeparatorAlwaysShown = newValue; 2621 fastPathCheckNeeded = true; 2622 } 2623 2624 /** 2625 * Returns whether the {@link #parse(java.lang.String, java.text.ParsePosition)} 2626 * method returns <code>BigDecimal</code>. The default value is false. 2627 * @see #setParseBigDecimal 2628 * @since 1.5 2629 */ 2630 public boolean isParseBigDecimal() { 2631 return parseBigDecimal; 2632 } 2633 2634 /** 2635 * Sets whether the {@link #parse(java.lang.String, java.text.ParsePosition)} 2636 * method returns <code>BigDecimal</code>. 2637 * @see #isParseBigDecimal 2638 * @since 1.5 2639 */ 2640 public void setParseBigDecimal(boolean newValue) { 2641 parseBigDecimal = newValue; 2642 } 2643 2644 /** 2645 * Standard override; no change in semantics. 2646 */ 2647 @Override 2648 public Object clone() { 2649 DecimalFormat other = (DecimalFormat) super.clone(); 2650 other.symbols = (DecimalFormatSymbols) symbols.clone(); 2651 other.digitList = (DigitList) digitList.clone(); 2652 2653 // Fast-path is almost stateless algorithm. The only logical state is the 2654 // isFastPath flag. In addition fastPathCheckNeeded is a sentinel flag 2655 // that forces recalculation of all fast-path fields when set to true. 2656 // 2657 // There is thus no need to clone all the fast-path fields. 2658 // We just only need to set fastPathCheckNeeded to true when cloning, 2659 // and init fastPathData to null as if it were a truly new instance. 2660 // Every fast-path field will be recalculated (only once) at next usage of 2661 // fast-path algorithm. 2662 other.fastPathCheckNeeded = true; 2663 other.isFastPath = false; 2664 other.fastPathData = null; 2665 2666 return other; 2667 } 2668 2669 /** 2670 * Overrides equals 2671 */ 2672 @Override 2673 public boolean equals(Object obj) 2674 { 2675 if (obj == null) 2676 return false; 2677 if (!super.equals(obj)) 2678 return false; // super does class check 2679 DecimalFormat other = (DecimalFormat) obj; 2680 return ((posPrefixPattern == other.posPrefixPattern && 2681 positivePrefix.equals(other.positivePrefix)) 2682 || (posPrefixPattern != null && 2683 posPrefixPattern.equals(other.posPrefixPattern))) 2684 && ((posSuffixPattern == other.posSuffixPattern && 2685 positiveSuffix.equals(other.positiveSuffix)) 2686 || (posSuffixPattern != null && 2687 posSuffixPattern.equals(other.posSuffixPattern))) 2688 && ((negPrefixPattern == other.negPrefixPattern && 2689 negativePrefix.equals(other.negativePrefix)) 2690 || (negPrefixPattern != null && 2691 negPrefixPattern.equals(other.negPrefixPattern))) 2692 && ((negSuffixPattern == other.negSuffixPattern && 2693 negativeSuffix.equals(other.negativeSuffix)) 2694 || (negSuffixPattern != null && 2695 negSuffixPattern.equals(other.negSuffixPattern))) 2696 && multiplier == other.multiplier 2697 && groupingSize == other.groupingSize 2698 && decimalSeparatorAlwaysShown == other.decimalSeparatorAlwaysShown 2699 && parseBigDecimal == other.parseBigDecimal 2700 && useExponentialNotation == other.useExponentialNotation 2701 && (!useExponentialNotation || 2702 minExponentDigits == other.minExponentDigits) 2703 && maximumIntegerDigits == other.maximumIntegerDigits 2704 && minimumIntegerDigits == other.minimumIntegerDigits 2705 && maximumFractionDigits == other.maximumFractionDigits 2706 && minimumFractionDigits == other.minimumFractionDigits 2707 && roundingMode == other.roundingMode 2708 && symbols.equals(other.symbols); 2709 } 2710 2711 /** 2712 * Overrides hashCode 2713 */ 2714 @Override 2715 public int hashCode() { 2716 return super.hashCode() * 37 + positivePrefix.hashCode(); 2717 // just enough fields for a reasonable distribution 2718 } 2719 2720 /** 2721 * Synthesizes a pattern string that represents the current state 2722 * of this Format object. 2723 * @see #applyPattern 2724 */ 2725 public String toPattern() { 2726 return toPattern( false ); 2727 } 2728 2729 /** 2730 * Synthesizes a localized pattern string that represents the current 2731 * state of this Format object. 2732 * @see #applyPattern 2733 */ 2734 public String toLocalizedPattern() { 2735 return toPattern( true ); 2736 } 2737 2738 /** 2739 * Expand the affix pattern strings into the expanded affix strings. If any 2740 * affix pattern string is null, do not expand it. This method should be 2741 * called any time the symbols or the affix patterns change in order to keep 2742 * the expanded affix strings up to date. 2743 */ 2744 private void expandAffixes() { 2745 // Reuse one StringBuffer for better performance 2746 StringBuffer buffer = new StringBuffer(); 2747 if (posPrefixPattern != null) { 2748 positivePrefix = expandAffix(posPrefixPattern, buffer); 2749 positivePrefixFieldPositions = null; 2750 } 2751 if (posSuffixPattern != null) { 2752 positiveSuffix = expandAffix(posSuffixPattern, buffer); 2753 positiveSuffixFieldPositions = null; 2754 } 2755 if (negPrefixPattern != null) { 2756 negativePrefix = expandAffix(negPrefixPattern, buffer); 2757 negativePrefixFieldPositions = null; 2758 } 2759 if (negSuffixPattern != null) { 2760 negativeSuffix = expandAffix(negSuffixPattern, buffer); 2761 negativeSuffixFieldPositions = null; 2762 } 2763 } 2764 2765 /** 2766 * Expand an affix pattern into an affix string. All characters in the 2767 * pattern are literal unless prefixed by QUOTE. The following characters 2768 * after QUOTE are recognized: PATTERN_PERCENT, PATTERN_PER_MILLE, 2769 * PATTERN_MINUS, and CURRENCY_SIGN. If CURRENCY_SIGN is doubled (QUOTE + 2770 * CURRENCY_SIGN + CURRENCY_SIGN), it is interpreted as an ISO 4217 2771 * currency code. Any other character after a QUOTE represents itself. 2772 * QUOTE must be followed by another character; QUOTE may not occur by 2773 * itself at the end of the pattern. 2774 * 2775 * @param pattern the non-null, possibly empty pattern 2776 * @param buffer a scratch StringBuffer; its contents will be lost 2777 * @return the expanded equivalent of pattern 2778 */ 2779 private String expandAffix(String pattern, StringBuffer buffer) { 2780 buffer.setLength(0); 2781 for (int i=0; i<pattern.length(); ) { 2782 char c = pattern.charAt(i++); 2783 if (c == QUOTE) { 2784 c = pattern.charAt(i++); 2785 switch (c) { 2786 case CURRENCY_SIGN: 2787 if (i<pattern.length() && 2788 pattern.charAt(i) == CURRENCY_SIGN) { 2789 ++i; 2790 buffer.append(symbols.getInternationalCurrencySymbol()); 2791 } else { 2792 buffer.append(symbols.getCurrencySymbol()); 2793 } 2794 continue; 2795 case PATTERN_PERCENT: 2796 c = symbols.getPercent(); 2797 break; 2798 case PATTERN_PER_MILLE: 2799 c = symbols.getPerMill(); 2800 break; 2801 case PATTERN_MINUS: 2802 c = symbols.getMinusSign(); 2803 break; 2804 } 2805 } 2806 buffer.append(c); 2807 } 2808 return buffer.toString(); 2809 } 2810 2811 /** 2812 * Expand an affix pattern into an array of FieldPositions describing 2813 * how the pattern would be expanded. 2814 * All characters in the 2815 * pattern are literal unless prefixed by QUOTE. The following characters 2816 * after QUOTE are recognized: PATTERN_PERCENT, PATTERN_PER_MILLE, 2817 * PATTERN_MINUS, and CURRENCY_SIGN. If CURRENCY_SIGN is doubled (QUOTE + 2818 * CURRENCY_SIGN + CURRENCY_SIGN), it is interpreted as an ISO 4217 2819 * currency code. Any other character after a QUOTE represents itself. 2820 * QUOTE must be followed by another character; QUOTE may not occur by 2821 * itself at the end of the pattern. 2822 * 2823 * @param pattern the non-null, possibly empty pattern 2824 * @return FieldPosition array of the resulting fields. 2825 */ 2826 private FieldPosition[] expandAffix(String pattern) { 2827 ArrayList<FieldPosition> positions = null; 2828 int stringIndex = 0; 2829 for (int i=0; i<pattern.length(); ) { 2830 char c = pattern.charAt(i++); 2831 if (c == QUOTE) { 2832 int field = -1; 2833 Format.Field fieldID = null; 2834 c = pattern.charAt(i++); 2835 switch (c) { 2836 case CURRENCY_SIGN: 2837 String string; 2838 if (i<pattern.length() && 2839 pattern.charAt(i) == CURRENCY_SIGN) { 2840 ++i; 2841 string = symbols.getInternationalCurrencySymbol(); 2842 } else { 2843 string = symbols.getCurrencySymbol(); 2844 } 2845 if (string.length() > 0) { 2846 if (positions == null) { 2847 positions = new ArrayList<>(2); 2848 } 2849 FieldPosition fp = new FieldPosition(Field.CURRENCY); 2850 fp.setBeginIndex(stringIndex); 2851 fp.setEndIndex(stringIndex + string.length()); 2852 positions.add(fp); 2853 stringIndex += string.length(); 2854 } 2855 continue; 2856 case PATTERN_PERCENT: 2857 c = symbols.getPercent(); 2858 field = -1; 2859 fieldID = Field.PERCENT; 2860 break; 2861 case PATTERN_PER_MILLE: 2862 c = symbols.getPerMill(); 2863 field = -1; 2864 fieldID = Field.PERMILLE; 2865 break; 2866 case PATTERN_MINUS: 2867 c = symbols.getMinusSign(); 2868 field = -1; 2869 fieldID = Field.SIGN; 2870 break; 2871 } 2872 if (fieldID != null) { 2873 if (positions == null) { 2874 positions = new ArrayList<>(2); 2875 } 2876 FieldPosition fp = new FieldPosition(fieldID, field); 2877 fp.setBeginIndex(stringIndex); 2878 fp.setEndIndex(stringIndex + 1); 2879 positions.add(fp); 2880 } 2881 } 2882 stringIndex++; 2883 } 2884 if (positions != null) { 2885 return positions.toArray(EmptyFieldPositionArray); 2886 } 2887 return EmptyFieldPositionArray; 2888 } 2889 2890 /** 2891 * Appends an affix pattern to the given StringBuffer, quoting special 2892 * characters as needed. Uses the internal affix pattern, if that exists, 2893 * or the literal affix, if the internal affix pattern is null. The 2894 * appended string will generate the same affix pattern (or literal affix) 2895 * when passed to toPattern(). 2896 * 2897 * @param buffer the affix string is appended to this 2898 * @param affixPattern a pattern such as posPrefixPattern; may be null 2899 * @param expAffix a corresponding expanded affix, such as positivePrefix. 2900 * Ignored unless affixPattern is null. If affixPattern is null, then 2901 * expAffix is appended as a literal affix. 2902 * @param localized true if the appended pattern should contain localized 2903 * pattern characters; otherwise, non-localized pattern chars are appended 2904 */ 2905 private void appendAffix(StringBuffer buffer, String affixPattern, 2906 String expAffix, boolean localized) { 2907 if (affixPattern == null) { 2908 appendAffix(buffer, expAffix, localized); 2909 } else { 2910 int i; 2911 for (int pos=0; pos<affixPattern.length(); pos=i) { 2912 i = affixPattern.indexOf(QUOTE, pos); 2913 if (i < 0) { 2914 appendAffix(buffer, affixPattern.substring(pos), localized); 2915 break; 2916 } 2917 if (i > pos) { 2918 appendAffix(buffer, affixPattern.substring(pos, i), localized); 2919 } 2920 char c = affixPattern.charAt(++i); 2921 ++i; 2922 if (c == QUOTE) { 2923 buffer.append(c); 2924 // Fall through and append another QUOTE below 2925 } else if (c == CURRENCY_SIGN && 2926 i<affixPattern.length() && 2927 affixPattern.charAt(i) == CURRENCY_SIGN) { 2928 ++i; 2929 buffer.append(c); 2930 // Fall through and append another CURRENCY_SIGN below 2931 } else if (localized) { 2932 switch (c) { 2933 case PATTERN_PERCENT: 2934 c = symbols.getPercent(); 2935 break; 2936 case PATTERN_PER_MILLE: 2937 c = symbols.getPerMill(); 2938 break; 2939 case PATTERN_MINUS: 2940 c = symbols.getMinusSign(); 2941 break; 2942 } 2943 } 2944 buffer.append(c); 2945 } 2946 } 2947 } 2948 2949 /** 2950 * Append an affix to the given StringBuffer, using quotes if 2951 * there are special characters. Single quotes themselves must be 2952 * escaped in either case. 2953 */ 2954 private void appendAffix(StringBuffer buffer, String affix, boolean localized) { 2955 boolean needQuote; 2956 if (localized) { 2957 needQuote = affix.indexOf(symbols.getZeroDigit()) >= 0 2958 || affix.indexOf(symbols.getGroupingSeparator()) >= 0 2959 || affix.indexOf(symbols.getDecimalSeparator()) >= 0 2960 || affix.indexOf(symbols.getPercent()) >= 0 2961 || affix.indexOf(symbols.getPerMill()) >= 0 2962 || affix.indexOf(symbols.getDigit()) >= 0 2963 || affix.indexOf(symbols.getPatternSeparator()) >= 0 2964 || affix.indexOf(symbols.getMinusSign()) >= 0 2965 || affix.indexOf(CURRENCY_SIGN) >= 0; 2966 } else { 2967 needQuote = affix.indexOf(PATTERN_ZERO_DIGIT) >= 0 2968 || affix.indexOf(PATTERN_GROUPING_SEPARATOR) >= 0 2969 || affix.indexOf(PATTERN_DECIMAL_SEPARATOR) >= 0 2970 || affix.indexOf(PATTERN_PERCENT) >= 0 2971 || affix.indexOf(PATTERN_PER_MILLE) >= 0 2972 || affix.indexOf(PATTERN_DIGIT) >= 0 2973 || affix.indexOf(PATTERN_SEPARATOR) >= 0 2974 || affix.indexOf(PATTERN_MINUS) >= 0 2975 || affix.indexOf(CURRENCY_SIGN) >= 0; 2976 } 2977 if (needQuote) buffer.append('\''); 2978 if (affix.indexOf('\'') < 0) buffer.append(affix); 2979 else { 2980 for (int j=0; j<affix.length(); ++j) { 2981 char c = affix.charAt(j); 2982 buffer.append(c); 2983 if (c == '\'') buffer.append(c); 2984 } 2985 } 2986 if (needQuote) buffer.append('\''); 2987 } 2988 2989 /** 2990 * Does the real work of generating a pattern. */ 2991 private String toPattern(boolean localized) { 2992 StringBuffer result = new StringBuffer(); 2993 for (int j = 1; j >= 0; --j) { 2994 if (j == 1) 2995 appendAffix(result, posPrefixPattern, positivePrefix, localized); 2996 else appendAffix(result, negPrefixPattern, negativePrefix, localized); 2997 int i; 2998 int digitCount = useExponentialNotation 2999 ? getMaximumIntegerDigits() 3000 : Math.max(groupingSize, getMinimumIntegerDigits())+1; 3001 for (i = digitCount; i > 0; --i) { 3002 if (i != digitCount && isGroupingUsed() && groupingSize != 0 && 3003 i % groupingSize == 0) { 3004 result.append(localized ? symbols.getGroupingSeparator() : 3005 PATTERN_GROUPING_SEPARATOR); 3006 } 3007 result.append(i <= getMinimumIntegerDigits() 3008 ? (localized ? symbols.getZeroDigit() : PATTERN_ZERO_DIGIT) 3009 : (localized ? symbols.getDigit() : PATTERN_DIGIT)); 3010 } 3011 if (getMaximumFractionDigits() > 0 || decimalSeparatorAlwaysShown) 3012 result.append(localized ? symbols.getDecimalSeparator() : 3013 PATTERN_DECIMAL_SEPARATOR); 3014 for (i = 0; i < getMaximumFractionDigits(); ++i) { 3015 if (i < getMinimumFractionDigits()) { 3016 result.append(localized ? symbols.getZeroDigit() : 3017 PATTERN_ZERO_DIGIT); 3018 } else { 3019 result.append(localized ? symbols.getDigit() : 3020 PATTERN_DIGIT); 3021 } 3022 } 3023 if (useExponentialNotation) 3024 { 3025 result.append(localized ? symbols.getExponentSeparator() : 3026 PATTERN_EXPONENT); 3027 for (i=0; i<minExponentDigits; ++i) 3028 result.append(localized ? symbols.getZeroDigit() : 3029 PATTERN_ZERO_DIGIT); 3030 } 3031 if (j == 1) { 3032 appendAffix(result, posSuffixPattern, positiveSuffix, localized); 3033 if ((negSuffixPattern == posSuffixPattern && // n == p == null 3034 negativeSuffix.equals(positiveSuffix)) 3035 || (negSuffixPattern != null && 3036 negSuffixPattern.equals(posSuffixPattern))) { 3037 if ((negPrefixPattern != null && posPrefixPattern != null && 3038 negPrefixPattern.equals("'-" + posPrefixPattern)) || 3039 (negPrefixPattern == posPrefixPattern && // n == p == null 3040 negativePrefix.equals(symbols.getMinusSign() + positivePrefix))) 3041 break; 3042 } 3043 result.append(localized ? symbols.getPatternSeparator() : 3044 PATTERN_SEPARATOR); 3045 } else appendAffix(result, negSuffixPattern, negativeSuffix, localized); 3046 } 3047 return result.toString(); 3048 } 3049 3050 /** 3051 * Apply the given pattern to this Format object. A pattern is a 3052 * short-hand specification for the various formatting properties. 3053 * These properties can also be changed individually through the 3054 * various setter methods. 3055 * <p> 3056 * There is no limit to integer digits set 3057 * by this routine, since that is the typical end-user desire; 3058 * use setMaximumInteger if you want to set a real value. 3059 * For negative numbers, use a second pattern, separated by a semicolon 3060 * <P>Example <code>"#,#00.0#"</code> -> 1,234.56 3061 * <P>This means a minimum of 2 integer digits, 1 fraction digit, and 3062 * a maximum of 2 fraction digits. 3063 * <p>Example: <code>"#,#00.0#;(#,#00.0#)"</code> for negatives in 3064 * parentheses. 3065 * <p>In negative patterns, the minimum and maximum counts are ignored; 3066 * these are presumed to be set in the positive pattern. 3067 * 3068 * @exception NullPointerException if <code>pattern</code> is null 3069 * @exception IllegalArgumentException if the given pattern is invalid. 3070 */ 3071 public void applyPattern(String pattern) { 3072 applyPattern(pattern, false); 3073 } 3074 3075 /** 3076 * Apply the given pattern to this Format object. The pattern 3077 * is assumed to be in a localized notation. A pattern is a 3078 * short-hand specification for the various formatting properties. 3079 * These properties can also be changed individually through the 3080 * various setter methods. 3081 * <p> 3082 * There is no limit to integer digits set 3083 * by this routine, since that is the typical end-user desire; 3084 * use setMaximumInteger if you want to set a real value. 3085 * For negative numbers, use a second pattern, separated by a semicolon 3086 * <P>Example <code>"#,#00.0#"</code> -> 1,234.56 3087 * <P>This means a minimum of 2 integer digits, 1 fraction digit, and 3088 * a maximum of 2 fraction digits. 3089 * <p>Example: <code>"#,#00.0#;(#,#00.0#)"</code> for negatives in 3090 * parentheses. 3091 * <p>In negative patterns, the minimum and maximum counts are ignored; 3092 * these are presumed to be set in the positive pattern. 3093 * 3094 * @exception NullPointerException if <code>pattern</code> is null 3095 * @exception IllegalArgumentException if the given pattern is invalid. 3096 */ 3097 public void applyLocalizedPattern(String pattern) { 3098 applyPattern(pattern, true); 3099 } 3100 3101 /** 3102 * Does the real work of applying a pattern. 3103 */ 3104 private void applyPattern(String pattern, boolean localized) { 3105 char zeroDigit = PATTERN_ZERO_DIGIT; 3106 char groupingSeparator = PATTERN_GROUPING_SEPARATOR; 3107 char decimalSeparator = PATTERN_DECIMAL_SEPARATOR; 3108 char percent = PATTERN_PERCENT; 3109 char perMill = PATTERN_PER_MILLE; 3110 char digit = PATTERN_DIGIT; 3111 char separator = PATTERN_SEPARATOR; 3112 String exponent = PATTERN_EXPONENT; 3113 char minus = PATTERN_MINUS; 3114 if (localized) { 3115 zeroDigit = symbols.getZeroDigit(); 3116 groupingSeparator = symbols.getGroupingSeparator(); 3117 decimalSeparator = symbols.getDecimalSeparator(); 3118 percent = symbols.getPercent(); 3119 perMill = symbols.getPerMill(); 3120 digit = symbols.getDigit(); 3121 separator = symbols.getPatternSeparator(); 3122 exponent = symbols.getExponentSeparator(); 3123 minus = symbols.getMinusSign(); 3124 } 3125 boolean gotNegative = false; 3126 decimalSeparatorAlwaysShown = false; 3127 isCurrencyFormat = false; 3128 useExponentialNotation = false; 3129 3130 // Two variables are used to record the subrange of the pattern 3131 // occupied by phase 1. This is used during the processing of the 3132 // second pattern (the one representing negative numbers) to ensure 3133 // that no deviation exists in phase 1 between the two patterns. 3134 int phaseOneStart = 0; 3135 int phaseOneLength = 0; 3136 3137 int start = 0; 3138 for (int j = 1; j >= 0 && start < pattern.length(); --j) { 3139 boolean inQuote = false; 3140 StringBuffer prefix = new StringBuffer(); 3141 StringBuffer suffix = new StringBuffer(); 3142 int decimalPos = -1; 3143 int multiplier = 1; 3144 int digitLeftCount = 0, zeroDigitCount = 0, digitRightCount = 0; 3145 byte groupingCount = -1; 3146 3147 // The phase ranges from 0 to 2. Phase 0 is the prefix. Phase 1 is 3148 // the section of the pattern with digits, decimal separator, 3149 // grouping characters. Phase 2 is the suffix. In phases 0 and 2, 3150 // percent, per mille, and currency symbols are recognized and 3151 // translated. The separation of the characters into phases is 3152 // strictly enforced; if phase 1 characters are to appear in the 3153 // suffix, for example, they must be quoted. 3154 int phase = 0; 3155 3156 // The affix is either the prefix or the suffix. 3157 StringBuffer affix = prefix; 3158 3159 for (int pos = start; pos < pattern.length(); ++pos) { 3160 char ch = pattern.charAt(pos); 3161 switch (phase) { 3162 case 0: 3163 case 2: 3164 // Process the prefix / suffix characters 3165 if (inQuote) { 3166 // A quote within quotes indicates either the closing 3167 // quote or two quotes, which is a quote literal. That 3168 // is, we have the second quote in 'do' or 'don''t'. 3169 if (ch == QUOTE) { 3170 if ((pos+1) < pattern.length() && 3171 pattern.charAt(pos+1) == QUOTE) { 3172 ++pos; 3173 affix.append("''"); // 'don''t' 3174 } else { 3175 inQuote = false; // 'do' 3176 } 3177 continue; 3178 } 3179 } else { 3180 // Process unquoted characters seen in prefix or suffix 3181 // phase. 3182 if (ch == digit || 3183 ch == zeroDigit || 3184 ch == groupingSeparator || 3185 ch == decimalSeparator) { 3186 phase = 1; 3187 if (j == 1) { 3188 phaseOneStart = pos; 3189 } 3190 --pos; // Reprocess this character 3191 continue; 3192 } else if (ch == CURRENCY_SIGN) { 3193 // Use lookahead to determine if the currency sign 3194 // is doubled or not. 3195 boolean doubled = (pos + 1) < pattern.length() && 3196 pattern.charAt(pos + 1) == CURRENCY_SIGN; 3197 if (doubled) { // Skip over the doubled character 3198 ++pos; 3199 } 3200 isCurrencyFormat = true; 3201 affix.append(doubled ? "'\u00A4\u00A4" : "'\u00A4"); 3202 continue; 3203 } else if (ch == QUOTE) { 3204 // A quote outside quotes indicates either the 3205 // opening quote or two quotes, which is a quote 3206 // literal. That is, we have the first quote in 'do' 3207 // or o''clock. 3208 if (ch == QUOTE) { 3209 if ((pos+1) < pattern.length() && 3210 pattern.charAt(pos+1) == QUOTE) { 3211 ++pos; 3212 affix.append("''"); // o''clock 3213 } else { 3214 inQuote = true; // 'do' 3215 } 3216 continue; 3217 } 3218 } else if (ch == separator) { 3219 // Don't allow separators before we see digit 3220 // characters of phase 1, and don't allow separators 3221 // in the second pattern (j == 0). 3222 if (phase == 0 || j == 0) { 3223 throw new IllegalArgumentException("Unquoted special character '" + 3224 ch + "' in pattern \"" + pattern + '"'); 3225 } 3226 start = pos + 1; 3227 pos = pattern.length(); 3228 continue; 3229 } 3230 3231 // Next handle characters which are appended directly. 3232 else if (ch == percent) { 3233 if (multiplier != 1) { 3234 throw new IllegalArgumentException("Too many percent/per mille characters in pattern \"" + 3235 pattern + '"'); 3236 } 3237 multiplier = 100; 3238 affix.append("'%"); 3239 continue; 3240 } else if (ch == perMill) { 3241 if (multiplier != 1) { 3242 throw new IllegalArgumentException("Too many percent/per mille characters in pattern \"" + 3243 pattern + '"'); 3244 } 3245 multiplier = 1000; 3246 affix.append("'\u2030"); 3247 continue; 3248 } else if (ch == minus) { 3249 affix.append("'-"); 3250 continue; 3251 } 3252 } 3253 // Note that if we are within quotes, or if this is an 3254 // unquoted, non-special character, then we usually fall 3255 // through to here. 3256 affix.append(ch); 3257 break; 3258 3259 case 1: 3260 // Phase one must be identical in the two sub-patterns. We 3261 // enforce this by doing a direct comparison. While 3262 // processing the first sub-pattern, we just record its 3263 // length. While processing the second, we compare 3264 // characters. 3265 if (j == 1) { 3266 ++phaseOneLength; 3267 } else { 3268 if (--phaseOneLength == 0) { 3269 phase = 2; 3270 affix = suffix; 3271 } 3272 continue; 3273 } 3274 3275 // Process the digits, decimal, and grouping characters. We 3276 // record five pieces of information. We expect the digits 3277 // to occur in the pattern ####0000.####, and we record the 3278 // number of left digits, zero (central) digits, and right 3279 // digits. The position of the last grouping character is 3280 // recorded (should be somewhere within the first two blocks 3281 // of characters), as is the position of the decimal point, 3282 // if any (should be in the zero digits). If there is no 3283 // decimal point, then there should be no right digits. 3284 if (ch == digit) { 3285 if (zeroDigitCount > 0) { 3286 ++digitRightCount; 3287 } else { 3288 ++digitLeftCount; 3289 } 3290 if (groupingCount >= 0 && decimalPos < 0) { 3291 ++groupingCount; 3292 } 3293 } else if (ch == zeroDigit) { 3294 if (digitRightCount > 0) { 3295 throw new IllegalArgumentException("Unexpected '0' in pattern \"" + 3296 pattern + '"'); 3297 } 3298 ++zeroDigitCount; 3299 if (groupingCount >= 0 && decimalPos < 0) { 3300 ++groupingCount; 3301 } 3302 } else if (ch == groupingSeparator) { 3303 groupingCount = 0; 3304 } else if (ch == decimalSeparator) { 3305 if (decimalPos >= 0) { 3306 throw new IllegalArgumentException("Multiple decimal separators in pattern \"" + 3307 pattern + '"'); 3308 } 3309 decimalPos = digitLeftCount + zeroDigitCount + digitRightCount; 3310 } else if (pattern.regionMatches(pos, exponent, 0, exponent.length())){ 3311 if (useExponentialNotation) { 3312 throw new IllegalArgumentException("Multiple exponential " + 3313 "symbols in pattern \"" + pattern + '"'); 3314 } 3315 useExponentialNotation = true; 3316 minExponentDigits = 0; 3317 3318 // Use lookahead to parse out the exponential part 3319 // of the pattern, then jump into phase 2. 3320 pos = pos+exponent.length(); 3321 while (pos < pattern.length() && 3322 pattern.charAt(pos) == zeroDigit) { 3323 ++minExponentDigits; 3324 ++phaseOneLength; 3325 ++pos; 3326 } 3327 3328 if ((digitLeftCount + zeroDigitCount) < 1 || 3329 minExponentDigits < 1) { 3330 throw new IllegalArgumentException("Malformed exponential " + 3331 "pattern \"" + pattern + '"'); 3332 } 3333 3334 // Transition to phase 2 3335 phase = 2; 3336 affix = suffix; 3337 --pos; 3338 continue; 3339 } else { 3340 phase = 2; 3341 affix = suffix; 3342 --pos; 3343 --phaseOneLength; 3344 continue; 3345 } 3346 break; 3347 } 3348 } 3349 3350 // Handle patterns with no '0' pattern character. These patterns 3351 // are legal, but must be interpreted. "##.###" -> "#0.###". 3352 // ".###" -> ".0##". 3353 /* We allow patterns of the form "####" to produce a zeroDigitCount 3354 * of zero (got that?); although this seems like it might make it 3355 * possible for format() to produce empty strings, format() checks 3356 * for this condition and outputs a zero digit in this situation. 3357 * Having a zeroDigitCount of zero yields a minimum integer digits 3358 * of zero, which allows proper round-trip patterns. That is, we 3359 * don't want "#" to become "#0" when toPattern() is called (even 3360 * though that's what it really is, semantically). 3361 */ 3362 if (zeroDigitCount == 0 && digitLeftCount > 0 && decimalPos >= 0) { 3363 // Handle "###.###" and "###." and ".###" 3364 int n = decimalPos; 3365 if (n == 0) { // Handle ".###" 3366 ++n; 3367 } 3368 digitRightCount = digitLeftCount - n; 3369 digitLeftCount = n - 1; 3370 zeroDigitCount = 1; 3371 } 3372 3373 // Do syntax checking on the digits. 3374 if ((decimalPos < 0 && digitRightCount > 0) || 3375 (decimalPos >= 0 && (decimalPos < digitLeftCount || 3376 decimalPos > (digitLeftCount + zeroDigitCount))) || 3377 groupingCount == 0 || inQuote) { 3378 throw new IllegalArgumentException("Malformed pattern \"" + 3379 pattern + '"'); 3380 } 3381 3382 if (j == 1) { 3383 posPrefixPattern = prefix.toString(); 3384 posSuffixPattern = suffix.toString(); 3385 negPrefixPattern = posPrefixPattern; // assume these for now 3386 negSuffixPattern = posSuffixPattern; 3387 int digitTotalCount = digitLeftCount + zeroDigitCount + digitRightCount; 3388 /* The effectiveDecimalPos is the position the decimal is at or 3389 * would be at if there is no decimal. Note that if decimalPos<0, 3390 * then digitTotalCount == digitLeftCount + zeroDigitCount. 3391 */ 3392 int effectiveDecimalPos = decimalPos >= 0 ? 3393 decimalPos : digitTotalCount; 3394 setMinimumIntegerDigits(effectiveDecimalPos - digitLeftCount); 3395 setMaximumIntegerDigits(useExponentialNotation ? 3396 digitLeftCount + getMinimumIntegerDigits() : 3397 MAXIMUM_INTEGER_DIGITS); 3398 setMaximumFractionDigits(decimalPos >= 0 ? 3399 (digitTotalCount - decimalPos) : 0); 3400 setMinimumFractionDigits(decimalPos >= 0 ? 3401 (digitLeftCount + zeroDigitCount - decimalPos) : 0); 3402 setGroupingUsed(groupingCount > 0); 3403 this.groupingSize = (groupingCount > 0) ? groupingCount : 0; 3404 this.multiplier = multiplier; 3405 setDecimalSeparatorAlwaysShown(decimalPos == 0 || 3406 decimalPos == digitTotalCount); 3407 } else { 3408 negPrefixPattern = prefix.toString(); 3409 negSuffixPattern = suffix.toString(); 3410 gotNegative = true; 3411 } 3412 } 3413 3414 if (pattern.length() == 0) { 3415 posPrefixPattern = posSuffixPattern = ""; 3416 setMinimumIntegerDigits(0); 3417 setMaximumIntegerDigits(MAXIMUM_INTEGER_DIGITS); 3418 setMinimumFractionDigits(0); 3419 setMaximumFractionDigits(MAXIMUM_FRACTION_DIGITS); 3420 } 3421 3422 // If there was no negative pattern, or if the negative pattern is 3423 // identical to the positive pattern, then prepend the minus sign to 3424 // the positive pattern to form the negative pattern. 3425 if (!gotNegative || 3426 (negPrefixPattern.equals(posPrefixPattern) 3427 && negSuffixPattern.equals(posSuffixPattern))) { 3428 negSuffixPattern = posSuffixPattern; 3429 negPrefixPattern = "'-" + posPrefixPattern; 3430 } 3431 3432 expandAffixes(); 3433 } 3434 3435 /** 3436 * Sets the maximum number of digits allowed in the integer portion of a 3437 * number. 3438 * For formatting numbers other than <code>BigInteger</code> and 3439 * <code>BigDecimal</code> objects, the lower of <code>newValue</code> and 3440 * 309 is used. Negative input values are replaced with 0. 3441 * @see NumberFormat#setMaximumIntegerDigits 3442 */ 3443 @Override 3444 public void setMaximumIntegerDigits(int newValue) { 3445 maximumIntegerDigits = Math.min(Math.max(0, newValue), MAXIMUM_INTEGER_DIGITS); 3446 super.setMaximumIntegerDigits((maximumIntegerDigits > DOUBLE_INTEGER_DIGITS) ? 3447 DOUBLE_INTEGER_DIGITS : maximumIntegerDigits); 3448 if (minimumIntegerDigits > maximumIntegerDigits) { 3449 minimumIntegerDigits = maximumIntegerDigits; 3450 super.setMinimumIntegerDigits((minimumIntegerDigits > DOUBLE_INTEGER_DIGITS) ? 3451 DOUBLE_INTEGER_DIGITS : minimumIntegerDigits); 3452 } 3453 fastPathCheckNeeded = true; 3454 } 3455 3456 /** 3457 * Sets the minimum number of digits allowed in the integer portion of a 3458 * number. 3459 * For formatting numbers other than <code>BigInteger</code> and 3460 * <code>BigDecimal</code> objects, the lower of <code>newValue</code> and 3461 * 309 is used. Negative input values are replaced with 0. 3462 * @see NumberFormat#setMinimumIntegerDigits 3463 */ 3464 @Override 3465 public void setMinimumIntegerDigits(int newValue) { 3466 minimumIntegerDigits = Math.min(Math.max(0, newValue), MAXIMUM_INTEGER_DIGITS); 3467 super.setMinimumIntegerDigits((minimumIntegerDigits > DOUBLE_INTEGER_DIGITS) ? 3468 DOUBLE_INTEGER_DIGITS : minimumIntegerDigits); 3469 if (minimumIntegerDigits > maximumIntegerDigits) { 3470 maximumIntegerDigits = minimumIntegerDigits; 3471 super.setMaximumIntegerDigits((maximumIntegerDigits > DOUBLE_INTEGER_DIGITS) ? 3472 DOUBLE_INTEGER_DIGITS : maximumIntegerDigits); 3473 } 3474 fastPathCheckNeeded = true; 3475 } 3476 3477 /** 3478 * Sets the maximum number of digits allowed in the fraction portion of a 3479 * number. 3480 * For formatting numbers other than <code>BigInteger</code> and 3481 * <code>BigDecimal</code> objects, the lower of <code>newValue</code> and 3482 * 340 is used. Negative input values are replaced with 0. 3483 * @see NumberFormat#setMaximumFractionDigits 3484 */ 3485 @Override 3486 public void setMaximumFractionDigits(int newValue) { 3487 maximumFractionDigits = Math.min(Math.max(0, newValue), MAXIMUM_FRACTION_DIGITS); 3488 super.setMaximumFractionDigits((maximumFractionDigits > DOUBLE_FRACTION_DIGITS) ? 3489 DOUBLE_FRACTION_DIGITS : maximumFractionDigits); 3490 if (minimumFractionDigits > maximumFractionDigits) { 3491 minimumFractionDigits = maximumFractionDigits; 3492 super.setMinimumFractionDigits((minimumFractionDigits > DOUBLE_FRACTION_DIGITS) ? 3493 DOUBLE_FRACTION_DIGITS : minimumFractionDigits); 3494 } 3495 fastPathCheckNeeded = true; 3496 } 3497 3498 /** 3499 * Sets the minimum number of digits allowed in the fraction portion of a 3500 * number. 3501 * For formatting numbers other than <code>BigInteger</code> and 3502 * <code>BigDecimal</code> objects, the lower of <code>newValue</code> and 3503 * 340 is used. Negative input values are replaced with 0. 3504 * @see NumberFormat#setMinimumFractionDigits 3505 */ 3506 @Override 3507 public void setMinimumFractionDigits(int newValue) { 3508 minimumFractionDigits = Math.min(Math.max(0, newValue), MAXIMUM_FRACTION_DIGITS); 3509 super.setMinimumFractionDigits((minimumFractionDigits > DOUBLE_FRACTION_DIGITS) ? 3510 DOUBLE_FRACTION_DIGITS : minimumFractionDigits); 3511 if (minimumFractionDigits > maximumFractionDigits) { 3512 maximumFractionDigits = minimumFractionDigits; 3513 super.setMaximumFractionDigits((maximumFractionDigits > DOUBLE_FRACTION_DIGITS) ? 3514 DOUBLE_FRACTION_DIGITS : maximumFractionDigits); 3515 } 3516 fastPathCheckNeeded = true; 3517 } 3518 3519 /** 3520 * Gets the maximum number of digits allowed in the integer portion of a 3521 * number. 3522 * For formatting numbers other than <code>BigInteger</code> and 3523 * <code>BigDecimal</code> objects, the lower of the return value and 3524 * 309 is used. 3525 * @see #setMaximumIntegerDigits 3526 */ 3527 @Override 3528 public int getMaximumIntegerDigits() { 3529 return maximumIntegerDigits; 3530 } 3531 3532 /** 3533 * Gets the minimum number of digits allowed in the integer portion of a 3534 * number. 3535 * For formatting numbers other than <code>BigInteger</code> and 3536 * <code>BigDecimal</code> objects, the lower of the return value and 3537 * 309 is used. 3538 * @see #setMinimumIntegerDigits 3539 */ 3540 @Override 3541 public int getMinimumIntegerDigits() { 3542 return minimumIntegerDigits; 3543 } 3544 3545 /** 3546 * Gets the maximum number of digits allowed in the fraction portion of a 3547 * number. 3548 * For formatting numbers other than <code>BigInteger</code> and 3549 * <code>BigDecimal</code> objects, the lower of the return value and 3550 * 340 is used. 3551 * @see #setMaximumFractionDigits 3552 */ 3553 @Override 3554 public int getMaximumFractionDigits() { 3555 return maximumFractionDigits; 3556 } 3557 3558 /** 3559 * Gets the minimum number of digits allowed in the fraction portion of a 3560 * number. 3561 * For formatting numbers other than <code>BigInteger</code> and 3562 * <code>BigDecimal</code> objects, the lower of the return value and 3563 * 340 is used. 3564 * @see #setMinimumFractionDigits 3565 */ 3566 @Override 3567 public int getMinimumFractionDigits() { 3568 return minimumFractionDigits; 3569 } 3570 3571 /** 3572 * Gets the currency used by this decimal format when formatting 3573 * currency values. 3574 * The currency is obtained by calling 3575 * {@link DecimalFormatSymbols#getCurrency DecimalFormatSymbols.getCurrency} 3576 * on this number format's symbols. 3577 * 3578 * @return the currency used by this decimal format, or <code>null</code> 3579 * @since 1.4 3580 */ 3581 @Override 3582 public Currency getCurrency() { 3583 return symbols.getCurrency(); 3584 } 3585 3586 /** 3587 * Sets the currency used by this number format when formatting 3588 * currency values. This does not update the minimum or maximum 3589 * number of fraction digits used by the number format. 3590 * The currency is set by calling 3591 * {@link DecimalFormatSymbols#setCurrency DecimalFormatSymbols.setCurrency} 3592 * on this number format's symbols. 3593 * 3594 * @param currency the new currency to be used by this decimal format 3595 * @exception NullPointerException if <code>currency</code> is null 3596 * @since 1.4 3597 */ 3598 @Override 3599 public void setCurrency(Currency currency) { 3600 if (currency != symbols.getCurrency()) { 3601 symbols.setCurrency(currency); 3602 if (isCurrencyFormat) { 3603 expandAffixes(); 3604 } 3605 } 3606 fastPathCheckNeeded = true; 3607 } 3608 3609 /** 3610 * Gets the {@link java.math.RoundingMode} used in this DecimalFormat. 3611 * 3612 * @return The <code>RoundingMode</code> used for this DecimalFormat. 3613 * @see #setRoundingMode(RoundingMode) 3614 * @since 1.6 3615 */ 3616 @Override 3617 public RoundingMode getRoundingMode() { 3618 return roundingMode; 3619 } 3620 3621 /** 3622 * Sets the {@link java.math.RoundingMode} used in this DecimalFormat. 3623 * 3624 * @param roundingMode The <code>RoundingMode</code> to be used 3625 * @see #getRoundingMode() 3626 * @exception NullPointerException if <code>roundingMode</code> is null. 3627 * @since 1.6 3628 */ 3629 @Override 3630 public void setRoundingMode(RoundingMode roundingMode) { 3631 if (roundingMode == null) { 3632 throw new NullPointerException(); 3633 } 3634 3635 this.roundingMode = roundingMode; 3636 digitList.setRoundingMode(roundingMode); 3637 fastPathCheckNeeded = true; 3638 } 3639 3640 /** 3641 * Reads the default serializable fields from the stream and performs 3642 * validations and adjustments for older serialized versions. The 3643 * validations and adjustments are: 3644 * <ol> 3645 * <li> 3646 * Verify that the superclass's digit count fields correctly reflect 3647 * the limits imposed on formatting numbers other than 3648 * <code>BigInteger</code> and <code>BigDecimal</code> objects. These 3649 * limits are stored in the superclass for serialization compatibility 3650 * with older versions, while the limits for <code>BigInteger</code> and 3651 * <code>BigDecimal</code> objects are kept in this class. 3652 * If, in the superclass, the minimum or maximum integer digit count is 3653 * larger than <code>DOUBLE_INTEGER_DIGITS</code> or if the minimum or 3654 * maximum fraction digit count is larger than 3655 * <code>DOUBLE_FRACTION_DIGITS</code>, then the stream data is invalid 3656 * and this method throws an <code>InvalidObjectException</code>. 3657 * <li> 3658 * If <code>serialVersionOnStream</code> is less than 4, initialize 3659 * <code>roundingMode</code> to {@link java.math.RoundingMode#HALF_EVEN 3660 * RoundingMode.HALF_EVEN}. This field is new with version 4. 3661 * <li> 3662 * If <code>serialVersionOnStream</code> is less than 3, then call 3663 * the setters for the minimum and maximum integer and fraction digits with 3664 * the values of the corresponding superclass getters to initialize the 3665 * fields in this class. The fields in this class are new with version 3. 3666 * <li> 3667 * If <code>serialVersionOnStream</code> is less than 1, indicating that 3668 * the stream was written by JDK 1.1, initialize 3669 * <code>useExponentialNotation</code> 3670 * to false, since it was not present in JDK 1.1. 3671 * <li> 3672 * Set <code>serialVersionOnStream</code> to the maximum allowed value so 3673 * that default serialization will work properly if this object is streamed 3674 * out again. 3675 * </ol> 3676 * 3677 * <p>Stream versions older than 2 will not have the affix pattern variables 3678 * <code>posPrefixPattern</code> etc. As a result, they will be initialized 3679 * to <code>null</code>, which means the affix strings will be taken as 3680 * literal values. This is exactly what we want, since that corresponds to 3681 * the pre-version-2 behavior. 3682 */ 3683 private void readObject(ObjectInputStream stream) 3684 throws IOException, ClassNotFoundException 3685 { 3686 stream.defaultReadObject(); 3687 digitList = new DigitList(); 3688 3689 // We force complete fast-path reinitialization when the instance is 3690 // deserialized. See clone() comment on fastPathCheckNeeded. 3691 fastPathCheckNeeded = true; 3692 isFastPath = false; 3693 fastPathData = null; 3694 3695 if (serialVersionOnStream < 4) { 3696 setRoundingMode(RoundingMode.HALF_EVEN); 3697 } else { 3698 setRoundingMode(getRoundingMode()); 3699 } 3700 3701 // We only need to check the maximum counts because NumberFormat 3702 // .readObject has already ensured that the maximum is greater than the 3703 // minimum count. 3704 if (super.getMaximumIntegerDigits() > DOUBLE_INTEGER_DIGITS || 3705 super.getMaximumFractionDigits() > DOUBLE_FRACTION_DIGITS) { 3706 throw new InvalidObjectException("Digit count out of range"); 3707 } 3708 if (serialVersionOnStream < 3) { 3709 setMaximumIntegerDigits(super.getMaximumIntegerDigits()); 3710 setMinimumIntegerDigits(super.getMinimumIntegerDigits()); 3711 setMaximumFractionDigits(super.getMaximumFractionDigits()); 3712 setMinimumFractionDigits(super.getMinimumFractionDigits()); 3713 } 3714 if (serialVersionOnStream < 1) { 3715 // Didn't have exponential fields 3716 useExponentialNotation = false; 3717 } 3718 serialVersionOnStream = currentSerialVersion; 3719 } 3720 3721 //---------------------------------------------------------------------- 3722 // INSTANCE VARIABLES 3723 //---------------------------------------------------------------------- 3724 3725 private transient DigitList digitList = new DigitList(); 3726 3727 /** 3728 * The symbol used as a prefix when formatting positive numbers, e.g. "+". 3729 * 3730 * @serial 3731 * @see #getPositivePrefix 3732 */ 3733 private String positivePrefix = ""; 3734 3735 /** 3736 * The symbol used as a suffix when formatting positive numbers. 3737 * This is often an empty string. 3738 * 3739 * @serial 3740 * @see #getPositiveSuffix 3741 */ 3742 private String positiveSuffix = ""; 3743 3744 /** 3745 * The symbol used as a prefix when formatting negative numbers, e.g. "-". 3746 * 3747 * @serial 3748 * @see #getNegativePrefix 3749 */ 3750 private String negativePrefix = "-"; 3751 3752 /** 3753 * The symbol used as a suffix when formatting negative numbers. 3754 * This is often an empty string. 3755 * 3756 * @serial 3757 * @see #getNegativeSuffix 3758 */ 3759 private String negativeSuffix = ""; 3760 3761 /** 3762 * The prefix pattern for non-negative numbers. This variable corresponds 3763 * to <code>positivePrefix</code>. 3764 * 3765 * <p>This pattern is expanded by the method <code>expandAffix()</code> to 3766 * <code>positivePrefix</code> to update the latter to reflect changes in 3767 * <code>symbols</code>. If this variable is <code>null</code> then 3768 * <code>positivePrefix</code> is taken as a literal value that does not 3769 * change when <code>symbols</code> changes. This variable is always 3770 * <code>null</code> for <code>DecimalFormat</code> objects older than 3771 * stream version 2 restored from stream. 3772 * 3773 * @serial 3774 * @since 1.3 3775 */ 3776 private String posPrefixPattern; 3777 3778 /** 3779 * The suffix pattern for non-negative numbers. This variable corresponds 3780 * to <code>positiveSuffix</code>. This variable is analogous to 3781 * <code>posPrefixPattern</code>; see that variable for further 3782 * documentation. 3783 * 3784 * @serial 3785 * @since 1.3 3786 */ 3787 private String posSuffixPattern; 3788 3789 /** 3790 * The prefix pattern for negative numbers. This variable corresponds 3791 * to <code>negativePrefix</code>. This variable is analogous to 3792 * <code>posPrefixPattern</code>; see that variable for further 3793 * documentation. 3794 * 3795 * @serial 3796 * @since 1.3 3797 */ 3798 private String negPrefixPattern; 3799 3800 /** 3801 * The suffix pattern for negative numbers. This variable corresponds 3802 * to <code>negativeSuffix</code>. This variable is analogous to 3803 * <code>posPrefixPattern</code>; see that variable for further 3804 * documentation. 3805 * 3806 * @serial 3807 * @since 1.3 3808 */ 3809 private String negSuffixPattern; 3810 3811 /** 3812 * The multiplier for use in percent, per mille, etc. 3813 * 3814 * @serial 3815 * @see #getMultiplier 3816 */ 3817 private int multiplier = 1; 3818 3819 /** 3820 * The number of digits between grouping separators in the integer 3821 * portion of a number. Must be greater than 0 if 3822 * <code>NumberFormat.groupingUsed</code> is true. 3823 * 3824 * @serial 3825 * @see #getGroupingSize 3826 * @see java.text.NumberFormat#isGroupingUsed 3827 */ 3828 private byte groupingSize = 3; // invariant, > 0 if useThousands 3829 3830 /** 3831 * If true, forces the decimal separator to always appear in a formatted 3832 * number, even if the fractional part of the number is zero. 3833 * 3834 * @serial 3835 * @see #isDecimalSeparatorAlwaysShown 3836 */ 3837 private boolean decimalSeparatorAlwaysShown = false; 3838 3839 /** 3840 * If true, parse returns BigDecimal wherever possible. 3841 * 3842 * @serial 3843 * @see #isParseBigDecimal 3844 * @since 1.5 3845 */ 3846 private boolean parseBigDecimal = false; 3847 3848 3849 /** 3850 * True if this object represents a currency format. This determines 3851 * whether the monetary decimal separator is used instead of the normal one. 3852 */ 3853 private transient boolean isCurrencyFormat = false; 3854 3855 /** 3856 * The <code>DecimalFormatSymbols</code> object used by this format. 3857 * It contains the symbols used to format numbers, e.g. the grouping separator, 3858 * decimal separator, and so on. 3859 * 3860 * @serial 3861 * @see #setDecimalFormatSymbols 3862 * @see java.text.DecimalFormatSymbols 3863 */ 3864 private DecimalFormatSymbols symbols = null; // LIU new DecimalFormatSymbols(); 3865 3866 /** 3867 * True to force the use of exponential (i.e. scientific) notation when formatting 3868 * numbers. 3869 * 3870 * @serial 3871 * @since 1.2 3872 */ 3873 private boolean useExponentialNotation; // Newly persistent in the Java 2 platform v.1.2 3874 3875 /** 3876 * FieldPositions describing the positive prefix String. This is 3877 * lazily created. Use <code>getPositivePrefixFieldPositions</code> 3878 * when needed. 3879 */ 3880 private transient FieldPosition[] positivePrefixFieldPositions; 3881 3882 /** 3883 * FieldPositions describing the positive suffix String. This is 3884 * lazily created. Use <code>getPositiveSuffixFieldPositions</code> 3885 * when needed. 3886 */ 3887 private transient FieldPosition[] positiveSuffixFieldPositions; 3888 3889 /** 3890 * FieldPositions describing the negative prefix String. This is 3891 * lazily created. Use <code>getNegativePrefixFieldPositions</code> 3892 * when needed. 3893 */ 3894 private transient FieldPosition[] negativePrefixFieldPositions; 3895 3896 /** 3897 * FieldPositions describing the negative suffix String. This is 3898 * lazily created. Use <code>getNegativeSuffixFieldPositions</code> 3899 * when needed. 3900 */ 3901 private transient FieldPosition[] negativeSuffixFieldPositions; 3902 3903 /** 3904 * The minimum number of digits used to display the exponent when a number is 3905 * formatted in exponential notation. This field is ignored if 3906 * <code>useExponentialNotation</code> is not true. 3907 * 3908 * @serial 3909 * @since 1.2 3910 */ 3911 private byte minExponentDigits; // Newly persistent in the Java 2 platform v.1.2 3912 3913 /** 3914 * The maximum number of digits allowed in the integer portion of a 3915 * <code>BigInteger</code> or <code>BigDecimal</code> number. 3916 * <code>maximumIntegerDigits</code> must be greater than or equal to 3917 * <code>minimumIntegerDigits</code>. 3918 * 3919 * @serial 3920 * @see #getMaximumIntegerDigits 3921 * @since 1.5 3922 */ 3923 private int maximumIntegerDigits = super.getMaximumIntegerDigits(); 3924 3925 /** 3926 * The minimum number of digits allowed in the integer portion of a 3927 * <code>BigInteger</code> or <code>BigDecimal</code> number. 3928 * <code>minimumIntegerDigits</code> must be less than or equal to 3929 * <code>maximumIntegerDigits</code>. 3930 * 3931 * @serial 3932 * @see #getMinimumIntegerDigits 3933 * @since 1.5 3934 */ 3935 private int minimumIntegerDigits = super.getMinimumIntegerDigits(); 3936 3937 /** 3938 * The maximum number of digits allowed in the fractional portion of a 3939 * <code>BigInteger</code> or <code>BigDecimal</code> number. 3940 * <code>maximumFractionDigits</code> must be greater than or equal to 3941 * <code>minimumFractionDigits</code>. 3942 * 3943 * @serial 3944 * @see #getMaximumFractionDigits 3945 * @since 1.5 3946 */ 3947 private int maximumFractionDigits = super.getMaximumFractionDigits(); 3948 3949 /** 3950 * The minimum number of digits allowed in the fractional portion of a 3951 * <code>BigInteger</code> or <code>BigDecimal</code> number. 3952 * <code>minimumFractionDigits</code> must be less than or equal to 3953 * <code>maximumFractionDigits</code>. 3954 * 3955 * @serial 3956 * @see #getMinimumFractionDigits 3957 * @since 1.5 3958 */ 3959 private int minimumFractionDigits = super.getMinimumFractionDigits(); 3960 3961 /** 3962 * The {@link java.math.RoundingMode} used in this DecimalFormat. 3963 * 3964 * @serial 3965 * @since 1.6 3966 */ 3967 private RoundingMode roundingMode = RoundingMode.HALF_EVEN; 3968 3969 // ------ DecimalFormat fields for fast-path for double algorithm ------ 3970 3971 /** 3972 * Helper inner utility class for storing the data used in the fast-path 3973 * algorithm. Almost all fields related to fast-path are encapsulated in 3974 * this class. 3975 * 3976 * Any {@code DecimalFormat} instance has a {@code fastPathData} 3977 * reference field that is null unless both the properties of the instance 3978 * are such that the instance is in the "fast-path" state, and a format call 3979 * has been done at least once while in this state. 3980 * 3981 * Almost all fields are related to the "fast-path" state only and don't 3982 * change until one of the instance properties is changed. 3983 * 3984 * {@code firstUsedIndex} and {@code lastFreeIndex} are the only 3985 * two fields that are used and modified while inside a call to 3986 * {@code fastDoubleFormat}. 3987 * 3988 */ 3989 private static class FastPathData { 3990 // --- Temporary fields used in fast-path, shared by several methods. 3991 3992 /** The first unused index at the end of the formatted result. */ 3993 int lastFreeIndex; 3994 3995 /** The first used index at the beginning of the formatted result */ 3996 int firstUsedIndex; 3997 3998 // --- State fields related to fast-path status. Changes due to a 3999 // property change only. Set by checkAndSetFastPathStatus() only. 4000 4001 /** Difference between locale zero and default zero representation. */ 4002 int zeroDelta; 4003 4004 /** Locale char for grouping separator. */ 4005 char groupingChar; 4006 4007 /** Fixed index position of last integral digit of formatted result */ 4008 int integralLastIndex; 4009 4010 /** Fixed index position of first fractional digit of formatted result */ 4011 int fractionalFirstIndex; 4012 4013 /** Fractional constants depending on decimal|currency state */ 4014 double fractionalScaleFactor; 4015 int fractionalMaxIntBound; 4016 4017 4018 /** The char array buffer that will contain the formatted result */ 4019 char[] fastPathContainer; 4020 4021 /** Suffixes recorded as char array for efficiency. */ 4022 char[] charsPositivePrefix; 4023 char[] charsNegativePrefix; 4024 char[] charsPositiveSuffix; 4025 char[] charsNegativeSuffix; 4026 boolean positiveAffixesRequired = true; 4027 boolean negativeAffixesRequired = true; 4028 } 4029 4030 /** The format fast-path status of the instance. Logical state. */ 4031 private transient boolean isFastPath = false; 4032 4033 /** Flag stating need of check and reinit fast-path status on next format call. */ 4034 private transient boolean fastPathCheckNeeded = true; 4035 4036 /** DecimalFormat reference to its FastPathData */ 4037 private transient FastPathData fastPathData; 4038 4039 4040 //---------------------------------------------------------------------- 4041 4042 static final int currentSerialVersion = 4; 4043 4044 /** 4045 * The internal serial version which says which version was written. 4046 * Possible values are: 4047 * <ul> 4048 * <li><b>0</b> (default): versions before the Java 2 platform v1.2 4049 * <li><b>1</b>: version for 1.2, which includes the two new fields 4050 * <code>useExponentialNotation</code> and 4051 * <code>minExponentDigits</code>. 4052 * <li><b>2</b>: version for 1.3 and later, which adds four new fields: 4053 * <code>posPrefixPattern</code>, <code>posSuffixPattern</code>, 4054 * <code>negPrefixPattern</code>, and <code>negSuffixPattern</code>. 4055 * <li><b>3</b>: version for 1.5 and later, which adds five new fields: 4056 * <code>maximumIntegerDigits</code>, 4057 * <code>minimumIntegerDigits</code>, 4058 * <code>maximumFractionDigits</code>, 4059 * <code>minimumFractionDigits</code>, and 4060 * <code>parseBigDecimal</code>. 4061 * <li><b>4</b>: version for 1.6 and later, which adds one new field: 4062 * <code>roundingMode</code>. 4063 * </ul> 4064 * @since 1.2 4065 * @serial 4066 */ 4067 private int serialVersionOnStream = currentSerialVersion; 4068 4069 //---------------------------------------------------------------------- 4070 // CONSTANTS 4071 //---------------------------------------------------------------------- 4072 4073 // ------ Fast-Path for double Constants ------ 4074 4075 /** Maximum valid integer value for applying fast-path algorithm */ 4076 private static final double MAX_INT_AS_DOUBLE = (double) Integer.MAX_VALUE; 4077 4078 /** 4079 * The digit arrays used in the fast-path methods for collecting digits. 4080 * Using 3 constants arrays of chars ensures a very fast collection of digits 4081 */ 4082 private static class DigitArrays { 4083 static final char[] DigitOnes1000 = new char[1000]; 4084 static final char[] DigitTens1000 = new char[1000]; 4085 static final char[] DigitHundreds1000 = new char[1000]; 4086 4087 // initialize on demand holder class idiom for arrays of digits 4088 static { 4089 int tenIndex = 0; 4090 int hundredIndex = 0; 4091 char digitOne = '0'; 4092 char digitTen = '0'; 4093 char digitHundred = '0'; 4094 for (int i = 0; i < 1000; i++ ) { 4095 4096 DigitOnes1000[i] = digitOne; 4097 if (digitOne == '9') 4098 digitOne = '0'; 4099 else 4100 digitOne++; 4101 4102 DigitTens1000[i] = digitTen; 4103 if (i == (tenIndex + 9)) { 4104 tenIndex += 10; 4105 if (digitTen == '9') 4106 digitTen = '0'; 4107 else 4108 digitTen++; 4109 } 4110 4111 DigitHundreds1000[i] = digitHundred; 4112 if (i == (hundredIndex + 99)) { 4113 digitHundred++; 4114 hundredIndex += 100; 4115 } 4116 } 4117 } 4118 } 4119 // ------ Fast-Path for double Constants end ------ 4120 4121 // Constants for characters used in programmatic (unlocalized) patterns. 4122 private static final char PATTERN_ZERO_DIGIT = '0'; 4123 private static final char PATTERN_GROUPING_SEPARATOR = ','; 4124 private static final char PATTERN_DECIMAL_SEPARATOR = '.'; 4125 private static final char PATTERN_PER_MILLE = '\u2030'; 4126 private static final char PATTERN_PERCENT = '%'; 4127 private static final char PATTERN_DIGIT = '#'; 4128 private static final char PATTERN_SEPARATOR = ';'; 4129 private static final String PATTERN_EXPONENT = "E"; 4130 private static final char PATTERN_MINUS = '-'; 4131 4132 /** 4133 * The CURRENCY_SIGN is the standard Unicode symbol for currency. It 4134 * is used in patterns and substituted with either the currency symbol, 4135 * or if it is doubled, with the international currency symbol. If the 4136 * CURRENCY_SIGN is seen in a pattern, then the decimal separator is 4137 * replaced with the monetary decimal separator. 4138 * 4139 * The CURRENCY_SIGN is not localized. 4140 */ 4141 private static final char CURRENCY_SIGN = '\u00A4'; 4142 4143 private static final char QUOTE = '\''; 4144 4145 private static FieldPosition[] EmptyFieldPositionArray = new FieldPosition[0]; 4146 4147 // Upper limit on integer and fraction digits for a Java double 4148 static final int DOUBLE_INTEGER_DIGITS = 309; 4149 static final int DOUBLE_FRACTION_DIGITS = 340; 4150 4151 // Upper limit on integer and fraction digits for BigDecimal and BigInteger 4152 static final int MAXIMUM_INTEGER_DIGITS = Integer.MAX_VALUE; 4153 static final int MAXIMUM_FRACTION_DIGITS = Integer.MAX_VALUE; 4154 4155 // Proclaim JDK 1.1 serial compatibility. 4156 static final long serialVersionUID = 864413376551465018L; 4157 4158 /** 4159 * Cache to hold the NumberPattern of a Locale. 4160 */ 4161 private static final ConcurrentMap<Locale, String> cachedLocaleData 4162 = new ConcurrentHashMap<>(3); 4163 }