1 /*
   2  * Copyright (c) 1997, 2023, 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.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  */
  23 
  24 /**
  25  * @test
  26  * @bug 4052223 4059870 4061302 4062486 4066646 4068693 4070798 4071005 4071014
  27  * 4071492 4071859 4074454 4074620 4075713 4083018 4086575 4087244 4087245
  28  * 4087251 4087535 4088161 4088503 4090489 4090504 4092480 4092561 4095713
  29  * 4098741 4099404 4101481 4106658 4106662 4106664 4108738 4110936 4122840
  30  * 4125885 4134034 4134300 4140009 4141750 4145457 4147295 4147706 4162198
  31  * 4162852 4167494 4170798 4176114 4179818 4185761 4212072 4212073 4216742
  32  * 4217661 4243011 4243108 4330377 4233840 4241880 4833877 8008577 8227313
  33  * @summary Regression tests for NumberFormat and associated classes
  34  * @library /java/text/testlib
  35  * @build HexDumpReader TestUtils
  36  * @modules java.base/sun.util.resources
  37  *          jdk.localedata
  38  * @compile -XDignore.symbol.file NumberRegression.java
  39  * @run junit/othervm -Djava.locale.providers=COMPAT,SPI NumberRegression
  40  */
  41 
  42 /*
  43 (C) Copyright Taligent, Inc. 1996 - All Rights Reserved
  44 (C) Copyright IBM Corp. 1996 - All Rights Reserved
  45 
  46   The original version of this source code and documentation is copyrighted and
  47 owned by Taligent, Inc., a wholly-owned subsidiary of IBM. These materials are
  48 provided under terms of a License Agreement between Taligent and Sun. This
  49 technology is protected by multiple US and International patents. This notice and
  50 attribution to Taligent may not be removed.
  51   Taligent is a registered trademark of Taligent, Inc.
  52 */
  53 
  54 import java.text.*;
  55 import java.util.*;
  56 import java.math.BigDecimal;
  57 import java.io.*;
  58 import java.math.BigInteger;
  59 import sun.util.resources.LocaleData;
  60 
  61 import org.junit.jupiter.api.Test;
  62 
  63 import static org.junit.jupiter.api.Assertions.fail;
  64 
  65 public class NumberRegression {
  66 
  67     /**
  68      * NumberFormat.equals comparing with null should always return false.
  69      */
  70     @Test
  71     public void Test4075713(){
  72 
  73         try {
  74             MyNumberFormatTest tmp = new MyNumberFormatTest();
  75             if (!tmp.equals(null))
  76                 System.out.println("NumberFormat.equals passed");
  77         } catch (NullPointerException e) {
  78             fail("(new MyNumberFormatTest()).equals(null) throws unexpected exception");
  79         }
  80     }
  81 
  82     /**
  83      * NumberFormat.equals comparing two obj equal even the setGroupingUsed
  84      * flag is different.
  85      */
  86     @Test
  87     public void Test4074620() {
  88 
  89         MyNumberFormatTest nf1 = new MyNumberFormatTest();
  90         MyNumberFormatTest nf2 = new MyNumberFormatTest();
  91 
  92         nf1.setGroupingUsed(false);
  93         nf2.setGroupingUsed(true);
  94 
  95         if (nf1.equals(nf2)) fail("Test for bug 4074620 failed");
  96         else System.out.println("Test for bug 4074620 passed.");
  97         return;
  98     }
  99 
 100 
 101     /**
 102      * DecimalFormat.format() incorrectly uses maxFractionDigits setting.
 103      */
 104 
 105     @Test
 106     public void Test4088161 (){
 107         Locale locale = Locale.getDefault();
 108         if (!TestUtils.usesAsciiDigits(locale)) {
 109             System.out.println("Skipping this test because locale is " + locale);
 110             return;
 111         }
 112 
 113         DecimalFormat df = new DecimalFormat();
 114         double d = 100;
 115         df.setMinimumFractionDigits(0);
 116         df.setMaximumFractionDigits(16);
 117         StringBuffer sBuf1 = new StringBuffer("");
 118         FieldPosition fp1 = new FieldPosition(0);
 119         System.out.println("d = " + d);
 120         System.out.println("maxFractionDigits = " + df.getMaximumFractionDigits());
 121         System.out.println(" format(d) = '" + df.format(d, sBuf1, fp1) + "'");
 122         df.setMaximumFractionDigits(17);
 123         StringBuffer sBuf2 = new StringBuffer("");
 124         FieldPosition fp2 = new FieldPosition(0);
 125         System.out.println("maxFractionDigits = " + df.getMaximumFractionDigits());
 126         df.format(d, sBuf2, fp2);
 127         String expected = "100";
 128         if (!sBuf2.toString().equals(expected))
 129             fail(" format(d) = '" + sBuf2 + "'");
 130     }
 131     /**
 132      * DecimalFormatSymbols should be cloned in the ctor DecimalFormat.
 133      * DecimalFormat(String, DecimalFormatSymbols).
 134      */
 135     @Test
 136     public void Test4087245 (){
 137         DecimalFormatSymbols symbols = DecimalFormatSymbols.getInstance();
 138         DecimalFormat df = new DecimalFormat("#,##0.0", symbols);
 139         long n = 123;
 140         StringBuffer buf1 = new StringBuffer();
 141         StringBuffer buf2 = new StringBuffer();
 142         System.out.println("format(" + n + ") = " +
 143         df.format(n, buf1, new FieldPosition(0)));
 144         symbols.setDecimalSeparator('p'); // change value of field
 145         System.out.println("format(" + n + ") = " +
 146         df.format(n, buf2, new FieldPosition(0)));
 147         if (!buf1.toString().equals(buf2.toString()))
 148             fail("Test for bug 4087245 failed");
 149     }
 150     /**
 151      * DecimalFormat.format() incorrectly formats 0.0
 152      */
 153     @Test
 154     public void Test4087535 ()
 155     {
 156         DecimalFormat df = new DecimalFormat();
 157         df.setMinimumIntegerDigits(0);
 158 
 159         double n = 0;
 160         String buffer = new String();
 161         buffer = df.format(n);
 162         if (buffer.length() == 0)
 163             fail(n + ": '" + buffer + "'");
 164         n = 0.1;
 165         buffer = df.format(n);
 166         if (buffer.length() == 0)
 167             fail(n + ": '" + buffer + "'");
 168     }
 169 
 170     /**
 171      * DecimalFormat.format fails when groupingSize is set to 0.
 172      */
 173     @Test
 174     public void Test4088503 (){
 175         DecimalFormat df = new DecimalFormat();
 176         df.setGroupingSize(0);
 177         StringBuffer sBuf = new StringBuffer("");
 178         FieldPosition fp = new FieldPosition(0);
 179         try {
 180             System.out.println(df.format(123, sBuf, fp).toString());
 181         } catch (Exception foo) {
 182             fail("Test for bug 4088503 failed.");
 183         }
 184 
 185     }
 186     /**
 187      * NumberFormat.getCurrencyInstance is wrong.
 188      */
 189     @Test
 190     public void Test4066646 () {
 191         float returnfloat = 0.0f;
 192         assignFloatValue(2.04f);
 193         assignFloatValue(2.03f);
 194         assignFloatValue(2.02f);
 195         assignFloatValue(0.0f);
 196     }
 197 
 198     public float assignFloatValue(float returnfloat)
 199     {
 200         System.out.println(" VALUE " + returnfloat);
 201         NumberFormat nfcommon =  NumberFormat.getCurrencyInstance(Locale.US);
 202         nfcommon.setGroupingUsed(false);
 203 
 204         String stringValue = nfcommon.format(returnfloat).substring(1);
 205         if (Float.valueOf(stringValue).floatValue() != returnfloat)
 206             fail(" DISPLAYVALUE " + stringValue);
 207         return returnfloat;
 208     } // End Of assignFloatValue()
 209 
 210     /**
 211      * DecimalFormat throws exception when parsing "0"
 212      */
 213     @Test
 214     public void Test4059870() {
 215         DecimalFormat format = new DecimalFormat("00");
 216         try {
 217             System.out.println(format.parse("0").toString());
 218         } catch (Exception e) { fail("Test for bug 4059870 failed : " + e); }
 219     }
 220     /**
 221      * DecimalFormatSymbol.equals should always return false when
 222      * comparing with null.
 223      */
 224 
 225     @Test
 226     public void Test4083018 (){
 227         DecimalFormatSymbols dfs = DecimalFormatSymbols.getInstance();
 228         try {
 229             if (!dfs.equals(null))
 230                 System.out.println("Test Passed!");
 231         } catch (Exception foo) {
 232             fail("Test for bug 4083018 failed => Message : " + foo.getMessage());
 233         }
 234     }
 235     /**
 236      * DecimalFormat does not round up correctly.
 237      */
 238     @Test
 239     public void Test4071492 (){
 240         Locale savedLocale = Locale.getDefault();
 241         Locale.setDefault(Locale.US);
 242         double x = 0.00159999;
 243         NumberFormat nf = NumberFormat.getInstance();
 244         nf.setMaximumFractionDigits(4);
 245         String out = nf.format(x);
 246         System.out.println("0.00159999 formats with 4 fractional digits to " + out);
 247         String expected = "0.0016";
 248         if (!out.equals(expected))
 249             fail("FAIL: Expected " + expected);
 250         Locale.setDefault(savedLocale);
 251     }
 252 
 253     /**
 254      * A space as a group separator for localized pattern causes
 255      * wrong format.  WorkAround : use non-breaking space.
 256      */
 257     @Test
 258     public void Test4086575() {
 259 
 260         NumberFormat nf = NumberFormat.getInstance(Locale.FRANCE);
 261         System.out.println("nf toPattern1: " + ((DecimalFormat)nf).toPattern());
 262         System.out.println("nf toLocPattern1: " + ((DecimalFormat)nf).toLocalizedPattern());
 263 
 264         // No group separator
 265         System.out.println("...applyLocalizedPattern ###,00;(###,00) ");
 266         ((DecimalFormat)nf).applyLocalizedPattern("###,00;(###,00)");
 267         System.out.println("nf toPattern2: " + ((DecimalFormat)nf).toPattern());
 268         System.out.println("nf toLocPattern2: " + ((DecimalFormat)nf).toLocalizedPattern());
 269 
 270         System.out.println("nf: " + nf.format(1234)); // 1234,00
 271         System.out.println("nf: " + nf.format(-1234)); // (1234,00)
 272 
 273         // Space as group separator
 274 
 275         System.out.println("...applyLocalizedPattern # ###,00;(# ###,00) ");
 276         ((DecimalFormat)nf).applyLocalizedPattern("#\u00a0###,00;(#\u00a0###,00)");
 277         System.out.println("nf toPattern2: " + ((DecimalFormat)nf).toPattern());
 278         System.out.println("nf toLocPattern2: " + ((DecimalFormat)nf).toLocalizedPattern());
 279         String buffer = nf.format(1234);
 280         if (!buffer.equals("1\u00a0234,00"))
 281             fail("nf : " + buffer); // Expect 1 234,00
 282         buffer = nf.format(-1234);
 283         if (!buffer.equals("(1\u00a0234,00)"))
 284             fail("nf : " + buffer); // Expect (1 234,00)
 285 
 286         // Erroneously prints:
 287         // 1234,00 ,
 288         // (1234,00 ,)
 289 
 290     }
 291     /**
 292      * DecimalFormat.parse returns wrong value
 293      */
 294     @Test
 295     public void Test4068693()
 296     {
 297         Locale savedLocale = Locale.getDefault();
 298         Locale.setDefault(Locale.US);
 299         System.out.println("----- Test Application -----");
 300         ParsePosition pos;
 301         DecimalFormat df = new DecimalFormat();
 302         Double d = (Double)df.parse("123.55456", pos=new ParsePosition(0));
 303         if (!d.toString().equals("123.55456")) {
 304             fail("Result -> " + d);
 305         }
 306         Locale.setDefault(savedLocale);
 307     }
 308 
 309     /* bugs 4069754, 4067878
 310      * null pointer thrown when accessing a deserialized DecimalFormat
 311      * object.
 312      */
 313     @Test
 314     public void Test4069754()
 315     {
 316         try {
 317             myformat it = new myformat();
 318             System.out.println(it.Now());
 319             FileOutputStream ostream = new FileOutputStream("t.tmp");
 320             ObjectOutputStream p = new ObjectOutputStream(ostream);
 321             p.writeObject(it);
 322             ostream.close();
 323             System.out.println("Saved ok.");
 324 
 325             FileInputStream istream = new FileInputStream("t.tmp");
 326             ObjectInputStream p2 = new ObjectInputStream(istream);
 327             myformat it2 = (myformat)p2.readObject();
 328             System.out.println(it2.Now());
 329             istream.close();
 330             System.out.println("Loaded ok.");
 331         } catch (Exception foo) {
 332             fail("Test for bug 4069754 or 4057878 failed => Exception: " + foo.getMessage());
 333         }
 334     }
 335 
 336     /**
 337      * DecimalFormat.applyPattern(String) allows illegal patterns
 338      */
 339     @Test
 340     public void Test4087251 (){
 341         DecimalFormat df = new DecimalFormat();
 342         try {
 343             df.applyPattern("#.#.#");
 344             System.out.println("toPattern() returns \"" + df.toPattern() + "\"");
 345             fail("applyPattern(\"#.#.#\") doesn't throw IllegalArgumentException");
 346         } catch (IllegalArgumentException e) {
 347             System.out.println("Caught Illegal Argument Error !");
 348         }
 349         // Second test; added 5/11/98 when reported to fail on 1.2b3
 350         try {
 351             df.applyPattern("#0.0#0#0");
 352             System.out.println("toPattern() returns \"" + df.toPattern() + "\"");
 353             fail("applyPattern(\"#0.0#0#0\") doesn't throw IllegalArgumentException");
 354         } catch (IllegalArgumentException e) {
 355             System.out.println("Ok - IllegalArgumentException for #0.0#0#0");
 356         }
 357     }
 358 
 359     /**
 360      * DecimalFormat.format() loses precision
 361      */
 362     @Test
 363     public void Test4090489 (){
 364         Locale savedLocale = Locale.getDefault();
 365         Locale.setDefault(Locale.US);
 366         DecimalFormat df = new DecimalFormat();
 367         df.setMinimumFractionDigits(10);
 368         df.setGroupingUsed(false);
 369         double d = 1.000000000000001E7;
 370         BigDecimal bd = new BigDecimal(d);
 371         StringBuffer sb = new StringBuffer("");
 372         FieldPosition fp = new FieldPosition(0);
 373         System.out.println("d = " + d);
 374         System.out.println("BigDecimal.toString():  " + bd.toString());
 375         df.format(d, sb, fp);
 376         if (!sb.toString().equals("10000000.0000000100")) {
 377             fail("DecimalFormat.format(): " + sb.toString());
 378         }
 379         Locale.setDefault(savedLocale);
 380     }
 381 
 382     /**
 383      * DecimalFormat.format() loses precision
 384      */
 385     @Test
 386     public void Test4090504 ()
 387     {
 388         double d = 1;
 389         System.out.println("d = " + d);
 390         DecimalFormat df = new DecimalFormat();
 391         StringBuffer sb;
 392         FieldPosition fp;
 393         try {
 394             for (int i = 17; i <= 20; i++) {
 395                 df.setMaximumFractionDigits(i);
 396                 sb = new StringBuffer("");
 397                 fp = new FieldPosition(0);
 398                 System.out.println("  getMaximumFractionDigits() = " + i);
 399                 System.out.println("  formated: " + df.format(d, sb, fp));
 400             }
 401         } catch (Exception foo) {
 402             fail("Bug 4090504 regression test failed. Message : " + foo.getMessage());
 403         }
 404     }
 405     /**
 406      * DecimalFormat.parse(String str, ParsePosition pp) loses precision
 407      */
 408     @Test
 409     public void Test4095713 ()
 410     {
 411         Locale savedLocale = Locale.getDefault();
 412         Locale.setDefault(Locale.US);
 413         DecimalFormat df = new DecimalFormat();
 414         String str = "0.1234";
 415         Double d1 = 0.1234;
 416         Double d2 = (Double) df.parse(str, new ParsePosition(0));
 417         System.out.println(d1.toString());
 418         if (d2.doubleValue() != d1.doubleValue())
 419             fail("Bug 4095713 test failed, new double value : " + d2);
 420         Locale.setDefault(savedLocale);
 421     }
 422 
 423     /**
 424      * DecimalFormat.parse() fails when multiplier is not set to 1
 425      */
 426     @Test
 427     public void Test4092561 ()
 428     {
 429         Locale savedLocale = Locale.getDefault();
 430         Locale.setDefault(Locale.US);
 431         DecimalFormat df = new DecimalFormat();
 432 
 433         String str = Long.toString(Long.MIN_VALUE);
 434         System.out.println("Long.MIN_VALUE : " + df.parse(str, new ParsePosition(0)).toString());
 435         df.setMultiplier(100);
 436         Number num = df.parse(str, new ParsePosition(0));
 437         if (num.doubleValue() != -9.223372036854776E16) {
 438             fail("Bug 4092561 test failed when multiplier is not set to 1. Expected: -9.223372036854776E16, got: " + num.doubleValue());
 439         }
 440 
 441         df.setMultiplier(-100);
 442         num = df.parse(str, new ParsePosition(0));
 443         if (num.doubleValue() != 9.223372036854776E16) {
 444             fail("Bug 4092561 test failed when multiplier is not set to 1. Expected: 9.223372036854776E16, got: " + num.doubleValue());
 445         }
 446 
 447         str = Long.toString(Long.MAX_VALUE);
 448         System.out.println("Long.MAX_VALUE : " + df.parse(str, new ParsePosition(0)).toString());
 449 
 450         df.setMultiplier(100);
 451         num = df.parse(str, new ParsePosition(0));
 452         if (num.doubleValue() != 9.223372036854776E16) {
 453             fail("Bug 4092561 test failed when multiplier is not set to 1. Expected: 9.223372036854776E16, got: " + num.doubleValue());
 454         }
 455 
 456         df.setMultiplier(-100);
 457         num = df.parse(str, new ParsePosition(0));
 458         if (num.doubleValue() != -9.223372036854776E16) {
 459             fail("Bug 4092561 test failed when multiplier is not set to 1. Expected: -9.223372036854776E16, got: " + num.doubleValue());
 460         }
 461 
 462         Locale.setDefault(savedLocale);
 463     }
 464 
 465     /**
 466      * DecimalFormat: Negative format ignored.
 467      */
 468     @Test
 469     public void Test4092480 ()
 470     {
 471         DecimalFormat dfFoo = new DecimalFormat("000");
 472 
 473         try {
 474             dfFoo.applyPattern("0000;-000");
 475             if (!dfFoo.toPattern().equals("#0000"))
 476                 fail("dfFoo.toPattern : " + dfFoo.toPattern());
 477             System.out.println(dfFoo.format(42));
 478             System.out.println(dfFoo.format(-42));
 479             dfFoo.applyPattern("000;-000");
 480             if (!dfFoo.toPattern().equals("#000"))
 481                 fail("dfFoo.toPattern : " + dfFoo.toPattern());
 482             System.out.println(dfFoo.format(42));
 483             System.out.println(dfFoo.format(-42));
 484 
 485             dfFoo.applyPattern("000;-0000");
 486             if (!dfFoo.toPattern().equals("#000"))
 487                 fail("dfFoo.toPattern : " + dfFoo.toPattern());
 488             System.out.println(dfFoo.format(42));
 489             System.out.println(dfFoo.format(-42));
 490 
 491             dfFoo.applyPattern("0000;-000");
 492             if (!dfFoo.toPattern().equals("#0000"))
 493                 fail("dfFoo.toPattern : " + dfFoo.toPattern());
 494             System.out.println(dfFoo.format(42));
 495             System.out.println(dfFoo.format(-42));
 496         } catch (Exception foo) {
 497             fail("Message " + foo.getMessage());
 498         }
 499     }
 500     /**
 501      * NumberFormat.getCurrencyInstance() produces format that uses
 502      * decimal separator instead of monetary decimal separator.
 503      *
 504      * Rewrote this test not to depend on the actual pattern.  Pattern should
 505      * never contain the monetary separator!  Decimal separator in pattern is
 506      * interpreted as monetary separator if currency symbol is seen!
 507      */
 508     @Test
 509     public void Test4087244 () {
 510         Locale de = Locale.of("pt", "PT");
 511         DecimalFormat df = (DecimalFormat) NumberFormat.getCurrencyInstance(de);
 512         DecimalFormatSymbols sym = df.getDecimalFormatSymbols();
 513         sym.setMonetaryDecimalSeparator('$');
 514         df.setDecimalFormatSymbols(sym);
 515         char decSep = sym.getDecimalSeparator();
 516         char monSep = sym.getMonetaryDecimalSeparator();
 517         char zero = sym.getZeroDigit();
 518         if (decSep == monSep) {
 519             fail("ERROR in test: want decimal sep != monetary sep");
 520         } else {
 521             df.setMinimumIntegerDigits(1);
 522             df.setMinimumFractionDigits(2);
 523             String str = df.format(1.23);
 524             String monStr = "1" + monSep + "23";
 525             String decStr = "1" + decSep + "23";
 526             if (str.indexOf(monStr) >= 0 && str.indexOf(decStr) < 0) {
 527                 System.out.println("OK: 1.23 -> \"" + str + "\" contains \"" +
 528                       monStr + "\" and not \"" + decStr + '"');
 529             } else {
 530                 fail("FAIL: 1.23 -> \"" + str + "\", should contain \"" +
 531                       monStr +
 532                       "\" and not \"" + decStr + '"');
 533             }
 534         }
 535     }
 536     /**
 537      * Number format data rounding errors for locale FR
 538      */
 539     @Test
 540     public void Test4070798 () {
 541         NumberFormat formatter;
 542         String tempString;
 543         /* User error :
 544         String expectedDefault = "-5\u00a0789,987";
 545         String expectedCurrency = "5\u00a0789,98 F";
 546         String expectedPercent = "-578\u00a0998%";
 547         */
 548         String expectedDefault = "-5\u00a0789,988";
 549         String expectedCurrency = "5\u00a0789,99 \u20AC";
 550         // changed for bug 6547501
 551         String expectedPercent = "-578\u00a0999 %";
 552 
 553         formatter = NumberFormat.getNumberInstance(Locale.FRANCE);
 554         tempString = formatter.format (-5789.9876);
 555 
 556         if (tempString.equals(expectedDefault)) {
 557             System.out.println("Bug 4070798 default test passed.");
 558         } else {
 559             fail("Failed:" +
 560             " Expected " + expectedDefault +
 561             " Received " + tempString );
 562         }
 563 
 564 
 565         formatter = NumberFormat.getCurrencyInstance(Locale.FRANCE);
 566         tempString = formatter.format( 5789.9876 );
 567 
 568         if (tempString.equals(expectedCurrency) ) {
 569             System.out.println("Bug 4070798 currency test assed.");
 570         } else {
 571             fail("Failed:" +
 572             " Expected " + expectedCurrency +
 573             " Received " + tempString );
 574         }
 575 
 576 
 577         formatter = NumberFormat.getPercentInstance(Locale.FRANCE);
 578         tempString = formatter.format (-5789.9876);
 579 
 580         if (tempString.equals(expectedPercent) ) {
 581             System.out.println("Bug 4070798 percentage test passed.");
 582         } else {
 583             fail("Failed:" +
 584             " Expected " + expectedPercent +
 585             " Received " + tempString );
 586         }
 587     }
 588     /**
 589      * Data rounding errors for French (Canada) locale
 590      */
 591     @Test
 592     public void Test4071005 () {
 593 
 594         NumberFormat formatter;
 595         String tempString;
 596     /* user error :
 597         String expectedDefault = "-5 789,987";
 598         String expectedCurrency = "5 789,98 $";
 599         String expectedPercent = "-578 998%";
 600     */
 601         String expectedDefault = "-5\u00a0789,988";
 602         String expectedCurrency = "5\u00a0789,99 $";
 603         // changed for bug 6547501
 604         String expectedPercent = "-578\u00a0999 %";
 605 
 606         formatter = NumberFormat.getNumberInstance(Locale.CANADA_FRENCH);
 607         tempString = formatter.format (-5789.9876);
 608         if (tempString.equals(expectedDefault)) {
 609             System.out.println("Bug 4071005 default test passed.");
 610         } else {
 611             fail("Failed:" +
 612             " Expected " + expectedDefault +
 613             " Received " + tempString );
 614         }
 615 
 616         formatter = NumberFormat.getCurrencyInstance(Locale.CANADA_FRENCH);
 617         tempString = formatter.format( 5789.9876 ) ;
 618 
 619         if (tempString.equals(expectedCurrency) ) {
 620             System.out.println("Bug 4071005 currency test passed.");
 621         } else {
 622             fail("Failed:" +
 623             " Expected " + expectedCurrency +
 624             " Received " + tempString );
 625         }
 626         formatter = NumberFormat.getPercentInstance(Locale.CANADA_FRENCH);
 627         tempString = formatter.format (-5789.9876);
 628 
 629         if (tempString.equals(expectedPercent) ) {
 630             System.out.println("Bug 4071005 percentage test passed.");
 631         } else {
 632             fail("Failed:" +
 633             " Expected " + expectedPercent +
 634             " Received " + tempString );
 635         }
 636     }
 637 
 638     /**
 639      * Data rounding errors for German (Germany) locale
 640      */
 641     @Test
 642     public void Test4071014 () {
 643         NumberFormat formatter;
 644         String tempString;
 645         /* user error :
 646         String expectedDefault = "-5.789,987";
 647         String expectedCurrency = "5.789,98 DM";
 648         String expectedPercent = "-578.998%";
 649         */
 650         String expectedDefault = "-5.789,988";
 651         String expectedCurrency = "5.789,99 \u20AC";
 652         String expectedPercent = "-578.999%";
 653 
 654         formatter = NumberFormat.getNumberInstance(Locale.GERMANY);
 655         tempString = formatter.format (-5789.9876);
 656 
 657         if (tempString.equals(expectedDefault)) {
 658             System.out.println("Bug 4071014 default test passed.");
 659         } else {
 660             fail("Failed:" +
 661             " Expected " + expectedDefault +
 662             " Received " + tempString );
 663         }
 664 
 665         formatter = NumberFormat.getCurrencyInstance(Locale.GERMANY);
 666         tempString = formatter.format( 5789.9876 ) ;
 667 
 668         if (tempString.equals(expectedCurrency) ) {
 669             System.out.println("Bug 4071014 currency test passed.");
 670         } else {
 671             fail("Failed:" +
 672             " Expected " + expectedCurrency +
 673             " Received " + tempString );
 674         }
 675 
 676         formatter = NumberFormat.getPercentInstance(Locale.GERMANY);
 677         tempString = formatter.format (-5789.9876);
 678 
 679         if (tempString.equals(expectedPercent) ) {
 680             System.out.println("Bug 4071014 percentage test passed.");
 681         } else {
 682             fail("Failed:" +
 683             " Expected " + expectedPercent +
 684             " Received " + tempString );
 685         }
 686 
 687     }
 688     /**
 689      * Data rounding errors for Italian locale number formats
 690      */
 691     @Test
 692     public void Test4071859 () {
 693         NumberFormat formatter;
 694         String tempString;
 695         /* user error :
 696         String expectedDefault = "-5.789,987";
 697         String expectedCurrency = "-L. 5.789,98";
 698         String expectedPercent = "-578.998%";
 699         */
 700         String expectedDefault = "-5.789,988";
 701         String expectedCurrency = "-\u20AC 5.789,99";
 702         String expectedPercent = "-578.999%";
 703 
 704         formatter = NumberFormat.getNumberInstance(Locale.ITALY);
 705         tempString = formatter.format (-5789.9876);
 706 
 707         if (tempString.equals(expectedDefault)) {
 708             System.out.println("Bug 4071859 default test passed.");
 709         } else {
 710             fail("Failed:" +
 711             " Expected " + expectedDefault +
 712             " Received " + tempString );
 713         }
 714 
 715         formatter = NumberFormat.getCurrencyInstance(Locale.ITALY);
 716         tempString = formatter.format( -5789.9876 ) ;
 717 
 718         if (tempString.equals(expectedCurrency) ) {
 719             System.out.println("Bug 4071859 currency test passed.");
 720         } else {
 721             fail("Failed:" +
 722             " Expected " + expectedCurrency +
 723             " Received " + tempString );
 724         }
 725 
 726         formatter = NumberFormat.getPercentInstance(Locale.ITALY);
 727         tempString = formatter.format (-5789.9876);
 728 
 729         if (tempString.equals(expectedPercent) ) {
 730             System.out.println("Bug 4071859 percentage test passed.");
 731         } else {
 732             fail("Failed:" +
 733             " Expected " + expectedPercent +
 734             " Received " + tempString );
 735         }
 736 
 737     }
 738 
 739     /* bug 4071859
 740      * Test rounding for nearest even.
 741      */
 742     @Test
 743     public void Test4093610()
 744     {
 745         Locale savedLocale = Locale.getDefault();
 746         Locale.setDefault(Locale.US);
 747         DecimalFormat df = new DecimalFormat("#0.#");
 748 
 749         roundingTest(df, 12.15, "12.2"); // Rounding-up. Above tie (12.150..)
 750         roundingTest(df, 12.25, "12.2"); // No round-up. Exact + half-even rule.
 751         roundingTest(df, 12.45, "12.4"); // No round-up. Below tie (12.449..)
 752         roundingTest(df, 12.450000001,"12.5"); // Rounding-up. Above tie.
 753         roundingTest(df, 12.55, "12.6"); // Rounding-up. Above tie (12.550..)
 754         roundingTest(df, 12.650000001,"12.7"); // Rounding-up. Above tie.
 755         roundingTest(df, 12.75, "12.8"); // Rounding-up. Exact + half-even rule.
 756         roundingTest(df, 12.750000001,"12.8"); // Rounding-up. Above tie.
 757         roundingTest(df, 12.85, "12.8"); // No round-up. Below tie (12.849..)
 758         roundingTest(df, 12.850000001,"12.9"); // Rounding-up. Above tie.
 759         roundingTest(df, 12.950000001,"13");   // Rounding-up. Above tie.
 760 
 761         Locale.setDefault(savedLocale);
 762     }
 763 
 764     void roundingTest(DecimalFormat df, double x, String expected)
 765     {
 766         String out = df.format(x);
 767         System.out.println("" + x + " formats with 1 fractional digits to " + out);
 768         if (!out.equals(expected)) fail("FAIL: Expected " + expected);
 769     }
 770     /**
 771      * Tests the setMaximumFractionDigits limit.
 772      */
 773     @Test
 774     public void Test4098741()
 775     {
 776         try {
 777             NumberFormat fmt = NumberFormat.getPercentInstance();
 778             fmt.setMaximumFractionDigits(20);
 779             System.out.println(fmt.format(.001));
 780         } catch (Exception foo) {
 781             fail("Bug 4098471 failed with exception thrown : " + foo.getMessage());
 782         }
 783     }
 784     /**
 785      * Tests illegal pattern exception.
 786      * Fix comment : HShih A31 Part1 will not be fixed and javadoc needs to be updated.
 787      * Part2 has been fixed.
 788      */
 789     @Test
 790     public void Test4074454()
 791     {
 792         Locale savedLocale = Locale.getDefault();
 793         Locale.setDefault(Locale.US);
 794         try {
 795             DecimalFormat fmt = new DecimalFormat("#,#00.00;-#.#");
 796             System.out.println("Inconsistent negative pattern is fine.");
 797             DecimalFormat newFmt = new DecimalFormat("#,#00.00 p''ieces;-#,#00.00 p''ieces");
 798             String tempString = newFmt.format(3456.78);
 799             if (!tempString.equals("3,456.78 p'ieces"))
 800                 fail("Failed!  3,456.78 p'ieces expected, but got : " + tempString);
 801         } catch (Exception foo) {
 802             fail("An exception was thrown for any inconsistent negative pattern.");
 803         }
 804         Locale.setDefault(savedLocale);
 805     }
 806 
 807     /**
 808      * Tests all different comments.
 809      * Response to some comments :
 810      * [1] DecimalFormat.parse API documentation is more than just one line.
 811      * This is not a reproducable doc error in 116 source code.
 812      * [2] See updated javadoc.
 813      * [3] Fixed.
 814      * [4] NumberFormat.parse(String, ParsePosition) : If parsing fails,
 815      * a null object will be returned.  The unchanged parse position also
 816      * reflects an error.
 817      * NumberFormat.parse(String) : If parsing fails, an ParseException
 818      * will be thrown.
 819      * See updated javadoc for more details.
 820      * [5] See updated javadoc.
 821      * [6] See updated javadoc.
 822      * [7] This is a correct behavior if the DateFormat object is linient.
 823      * Otherwise, an IllegalArgumentException will be thrown when formatting
 824      * "January 35".  See GregorianCalendar class javadoc for more details.
 825      */
 826     @Test
 827     public void Test4099404()
 828     {
 829         try {
 830             DecimalFormat fmt = new DecimalFormat("000.0#0");
 831             fail("Bug 4099404 failed applying illegal pattern \"000.0#0\"");
 832         } catch (Exception foo) {
 833             System.out.println("Bug 4099404 pattern \"000.0#0\" passed");
 834         }
 835         try {
 836             DecimalFormat fmt = new DecimalFormat("0#0.000");
 837             fail("Bug 4099404 failed applying illegal pattern \"0#0.000\"");
 838         } catch (Exception foo) {
 839             System.out.println("Bug 4099404 pattern \"0#0.000\" passed");
 840         }
 841     }
 842     /**
 843      * DecimalFormat.applyPattern doesn't set minimum integer digits
 844      */
 845     @Test
 846     public void Test4101481()
 847     {
 848         DecimalFormat sdf = new DecimalFormat("#,##0");
 849         if (sdf.getMinimumIntegerDigits() != 1)
 850             fail("Minimum integer digits : " + sdf.getMinimumIntegerDigits());
 851     }
 852     /**
 853      * Tests ParsePosition.setErrorPosition() and ParsePosition.getErrorPosition().
 854      */
 855     @Test
 856     public void Test4052223()
 857     {
 858         try {
 859             DecimalFormat fmt = new DecimalFormat("#,#00.00");
 860             Number num = fmt.parse("abc3");
 861             fail("Bug 4052223 failed : can't parse string \"a\".  Got " + num);
 862         } catch (ParseException foo) {
 863             System.out.println("Caught expected ParseException : " + foo.getMessage() + " at index : " + foo.getErrorOffset());
 864         }
 865     }
 866     /**
 867      * API tests for API addition request A9.
 868      */
 869     @Test
 870     public void Test4061302()
 871     {
 872         DecimalFormatSymbols fmt = DecimalFormatSymbols.getInstance();
 873         String currency = fmt.getCurrencySymbol();
 874         String intlCurrency = fmt.getInternationalCurrencySymbol();
 875         char monDecSeparator = fmt.getMonetaryDecimalSeparator();
 876         if (currency.equals("") ||
 877             intlCurrency.equals("") ||
 878             monDecSeparator == 0) {
 879             fail("getCurrencySymbols failed, got empty string.");
 880         }
 881         System.out.println("Before set ==> Currency : " + currency + " Intl Currency : " + intlCurrency + " Monetary Decimal Separator : " + monDecSeparator);
 882         fmt.setCurrencySymbol("XYZ");
 883         fmt.setInternationalCurrencySymbol("ABC");
 884         fmt.setMonetaryDecimalSeparator('*');
 885         currency = fmt.getCurrencySymbol();
 886         intlCurrency = fmt.getInternationalCurrencySymbol();
 887         monDecSeparator = fmt.getMonetaryDecimalSeparator();
 888         if (!currency.equals("XYZ") ||
 889             !intlCurrency.equals("ABC") ||
 890             monDecSeparator != '*') {
 891             fail("setCurrencySymbols failed.");
 892         }
 893         System.out.println("After set ==> Currency : " + currency + " Intl Currency : " + intlCurrency + " Monetary Decimal Separator : " + monDecSeparator);
 894     }
 895     /**
 896      * API tests for API addition request A23. FieldPosition.getBeginIndex and
 897      * FieldPosition.getEndIndex.
 898      */
 899     @Test
 900     public void Test4062486()
 901     {
 902         DecimalFormat fmt = new DecimalFormat("#,##0.00");
 903         StringBuffer formatted = new StringBuffer();
 904         FieldPosition field = new FieldPosition(0);
 905         Double num = 1234.5;
 906         fmt.format(num, formatted, field);
 907         if (field.getBeginIndex() != 0 && field.getEndIndex() != 5)
 908             fail("Format 1234.5 failed. Begin index: " + field.getBeginIndex() + " End index: " + field.getEndIndex());
 909         field.setBeginIndex(7);
 910         field.setEndIndex(4);
 911         if (field.getBeginIndex() != 7 && field.getEndIndex() != 4)
 912             fail("Set begin/end field indexes failed. Begin index: " + field.getBeginIndex() + " End index: " + field.getEndIndex());
 913     }
 914 
 915     /**
 916      * DecimalFormat.parse incorrectly works with a group separator.
 917      */
 918     @Test
 919     public void Test4108738()
 920     {
 921 
 922         DecimalFormat df = new DecimalFormat("#,##0.###",
 923         DecimalFormatSymbols.getInstance(java.util.Locale.US));
 924         String text = "1.222,111";
 925         Number num = df.parse(text,new ParsePosition(0));
 926         if (!num.toString().equals("1.222"))
 927             fail("\"" + text + "\"  is parsed as " + num);
 928         text = "1.222x111";
 929         num = df.parse(text,new ParsePosition(0));
 930         if (!num.toString().equals("1.222"))
 931             fail("\"" + text + "\"  is parsed as " + num);
 932     }
 933 
 934     /**
 935      * DecimalFormat.format() incorrectly formats negative doubles.
 936      */
 937     @Test
 938     public void Test4106658()
 939     {
 940         Locale savedLocale = Locale.getDefault();
 941         Locale.setDefault(Locale.US);
 942         DecimalFormat df = new DecimalFormat(); // Corrected; see 4147706
 943         double d1 = -0.0;
 944         double d2 = -0.0001;
 945         StringBuffer buffer = new StringBuffer();
 946         System.out.println("pattern: \"" + df.toPattern() + "\"");
 947         df.format(d1, buffer, new FieldPosition(0));
 948         if (!buffer.toString().equals("-0")) { // Corrected; see 4147706
 949             fail(d1 + "      is formatted as " + buffer);
 950         }
 951         buffer.setLength(0);
 952         df.format(d2, buffer, new FieldPosition(0));
 953         if (!buffer.toString().equals("-0")) { // Corrected; see 4147706
 954             fail(d2 + "      is formatted as " + buffer);
 955         }
 956         Locale.setDefault(savedLocale);
 957     }
 958 
 959     /**
 960      * DecimalFormat.parse returns 0 if string parameter is incorrect.
 961      */
 962     @Test
 963     public void Test4106662()
 964     {
 965         DecimalFormat df = new DecimalFormat();
 966         String text = "x";
 967         ParsePosition pos1 = new ParsePosition(0), pos2 = new ParsePosition(0);
 968 
 969         System.out.println("pattern: \"" + df.toPattern() + "\"");
 970         Number num = df.parse(text, pos1);
 971         if (num != null) {
 972             fail("Test Failed: \"" + text + "\" is parsed as " + num);
 973         }
 974         df = null;
 975         df = new DecimalFormat("$###.00");
 976         num = df.parse("$", pos2);
 977         if (num != null){
 978             fail("Test Failed: \"$\" is parsed as " + num);
 979         }
 980     }
 981 
 982     /**
 983      * NumberFormat.parse doesn't return null
 984      */
 985     @Test
 986     public void Test4114639()
 987     {
 988         NumberFormat format = NumberFormat.getInstance();
 989         String text = "time 10:x";
 990         ParsePosition pos = new ParsePosition(8);
 991         Number result = format.parse(text, pos);
 992         if (result != null) fail("Should return null but got : " + result); // Should be null; it isn't
 993     }
 994 
 995     /**
 996      * DecimalFormat.format(long n) fails if n * multiplier > MAX_LONG.
 997      */
 998     @Test
 999     public void Test4106664()
1000     {
1001         DecimalFormat df = new DecimalFormat();
1002         long n = 1234567890123456L;
1003         int m = 12345678;
1004         BigInteger bigN = BigInteger.valueOf(n);
1005         bigN = bigN.multiply(BigInteger.valueOf(m));
1006         df.setMultiplier(m);
1007         df.setGroupingUsed(false);
1008         System.out.println("formated: " +
1009             df.format(n, new StringBuffer(), new FieldPosition(0)));
1010         System.out.println("expected: " + bigN.toString());
1011     }
1012     /**
1013      * DecimalFormat.format incorrectly formats -0.0.
1014      */
1015     @Test
1016     public void Test4106667()
1017     {
1018         Locale savedLocale = Locale.getDefault();
1019         Locale.setDefault(Locale.US);
1020         DecimalFormat df = new DecimalFormat();
1021         df.setPositivePrefix("+");
1022         double d = -0.0;
1023         System.out.println("pattern: \"" + df.toPattern() + "\"");
1024         StringBuffer buffer = new StringBuffer();
1025         df.format(d, buffer, new FieldPosition(0));
1026         if (!buffer.toString().equals("-0")) { // Corrected; see 4147706
1027             fail(d + "  is formatted as " + buffer);
1028         }
1029         Locale.setDefault(savedLocale);
1030     }
1031 
1032     /**
1033      * DecimalFormat.setMaximumIntegerDigits() works incorrectly.
1034      */
1035     @Test
1036     public void Test4110936()
1037     {
1038         NumberFormat nf = NumberFormat.getInstance();
1039         nf.setMaximumIntegerDigits(128);
1040         System.out.println("setMaximumIntegerDigits(128)");
1041         if (nf.getMaximumIntegerDigits() != 128)
1042             fail("getMaximumIntegerDigits() returns " +
1043                 nf.getMaximumIntegerDigits());
1044     }
1045 
1046     /**
1047      * Locale data should use generic currency symbol
1048      *
1049      * 1) Make sure that all currency formats use the generic currency symbol.
1050      * 2) Make sure we get the same results using the generic symbol or a
1051      *    hard-coded one.
1052      */
1053     @Test
1054     public void Test4122840()
1055     {
1056         Locale[] locales = NumberFormat.getAvailableLocales();
1057 
1058         for (int i = 0; i < locales.length; i++) {
1059             ResourceBundle rb = LocaleData.getBundle("sun.text.resources.FormatData",
1060                                                      locales[i]);
1061             //
1062             // Get the currency pattern for this locale.  We have to fish it
1063             // out of the ResourceBundle directly, since DecimalFormat.toPattern
1064             // will return the localized symbol, not \00a4
1065             //
1066             String[] numPatterns = (String[])rb.getObject("NumberPatterns");
1067             String pattern = numPatterns[1];
1068 
1069             if (pattern.indexOf("\u00A4") == -1 ) {
1070                 fail("Currency format for " + locales[i] +
1071                         " does not contain generic currency symbol:" +
1072                         pattern );
1073             }
1074 
1075             // Create a DecimalFormat using the pattern we got and format a number
1076             DecimalFormatSymbols symbols = DecimalFormatSymbols.getInstance(locales[i]);
1077             DecimalFormat fmt1 = new DecimalFormat(pattern, symbols);
1078 
1079             String result1 = fmt1.format(1.111);
1080 
1081             //
1082             // Now substitute in the locale's currency symbol and create another
1083             // pattern.  Replace the decimal separator with the monetary separator.
1084             //
1085             char decSep = symbols.getDecimalSeparator();
1086             char monSep = symbols.getMonetaryDecimalSeparator();
1087             StringBuffer buf = new StringBuffer(pattern);
1088             for (int j = 0; j < buf.length(); j++) {
1089                 if (buf.charAt(j) == '\u00a4') {
1090                     String cur = "'" + symbols.getCurrencySymbol() + "'";
1091                     buf.replace(j, j+1, cur);
1092                     j += cur.length() - 1;
1093                 }
1094             }
1095             symbols.setDecimalSeparator(monSep);
1096             DecimalFormat fmt2 = new DecimalFormat(buf.toString(), symbols);
1097 
1098             String result2 = fmt2.format(1.111);
1099 
1100             if (!result1.equals(result2)) {
1101                 fail("Results for " + locales[i] + " differ: " +
1102                       result1 + " vs " + result2);
1103             }
1104         }
1105     }
1106 
1107     /**
1108      * DecimalFormat.format() delivers wrong string.
1109      */
1110     @Test
1111     public void Test4125885()
1112     {
1113         Locale savedLocale = Locale.getDefault();
1114         Locale.setDefault(Locale.US);
1115         double rate = 12.34;
1116         DecimalFormat formatDec = new DecimalFormat ("000.00");
1117         System.out.println("toPattern: " + formatDec.toPattern());
1118         String rateString= formatDec.format(rate);
1119         if (!rateString.equals("012.34"))
1120             fail("result : " + rateString + " expected : 012.34");
1121         rate = 0.1234;
1122         formatDec = null;
1123         formatDec = new DecimalFormat ("+000.00%;-000.00%");
1124         System.out.println("toPattern: " + formatDec.toPattern());
1125         rateString= formatDec.format(rate);
1126         if (!rateString.equals("+012.34%"))
1127             fail("result : " + rateString + " expected : +012.34%");
1128         Locale.setDefault(savedLocale);
1129     }
1130 
1131     /**
1132      **
1133      * DecimalFormat produces extra zeros when formatting numbers.
1134      */
1135     @Test
1136     public void Test4134034() {
1137         Locale savedLocale = Locale.getDefault();
1138         Locale.setDefault(Locale.US);
1139         DecimalFormat nf = new DecimalFormat("##,###,###.00");
1140 
1141         String f = nf.format(9.02);
1142         if (f.equals("9.02")) System.out.println(f + " ok"); else fail("9.02 -> " + f + "; want 9.02");
1143 
1144         f = nf.format(0);
1145         if (f.equals(".00")) System.out.println(f + " ok"); else fail("0 -> " + f + "; want .00");
1146         Locale.setDefault(savedLocale);
1147     }
1148 
1149     /**
1150      * CANNOT REPRODUCE - This bug could not be reproduced.  It may be
1151      * a duplicate of 4134034.
1152      *
1153      * JDK 1.1.6 Bug, did NOT occur in 1.1.5
1154      * Possibly related to bug 4125885.
1155      *
1156      * This class demonstrates a regression in version 1.1.6
1157      * of DecimalFormat class.
1158      *
1159      * 1.1.6 Results
1160      * Value 1.2 Format #.00 Result '01.20' !!!wrong
1161      * Value 1.2 Format 0.00 Result '001.20' !!!wrong
1162      * Value 1.2 Format 00.00 Result '0001.20' !!!wrong
1163      * Value 1.2 Format #0.0# Result '1.2'
1164      * Value 1.2 Format #0.00 Result '001.20' !!!wrong
1165      *
1166      * 1.1.5 Results
1167      * Value 1.2 Format #.00 Result '1.20'
1168      * Value 1.2 Format 0.00 Result '1.20'
1169      * Value 1.2 Format 00.00 Result '01.20'
1170      * Value 1.2 Format #0.0# Result '1.2'
1171      * Value 1.2 Format #0.00 Result '1.20'
1172      */
1173     @Test
1174     public void Test4134300() {
1175         Locale savedLocale = Locale.getDefault();
1176         Locale.setDefault(Locale.US);
1177         String[] DATA = {
1178          // Pattern      Expected string
1179             "#.00",      "1.20",
1180             "0.00",      "1.20",
1181             "00.00",     "01.20",
1182             "#0.0#",     "1.2",
1183             "#0.00",     "1.20",
1184         };
1185         for (int i=0; i<DATA.length; i+=2) {
1186             String result = new DecimalFormat(DATA[i]).format(1.2);
1187             if (!result.equals(DATA[i+1])) {
1188                 fail("Fail: 1.2 x " + DATA[i] + " = " + result +
1189                       "; want " + DATA[i+1]);
1190             }
1191             else {
1192                 System.out.println("Ok: 1.2 x " + DATA[i] + " = " + result);
1193             }
1194         }
1195         Locale.setDefault(savedLocale);
1196     }
1197 
1198     /**
1199      * Empty pattern produces double negative prefix.
1200      */
1201     @Test
1202     public void Test4140009() {
1203         for (int i=0; i<2; ++i) {
1204             DecimalFormat f = null;
1205             switch (i) {
1206             case 0:
1207                 f = new DecimalFormat("",
1208                             DecimalFormatSymbols.getInstance(Locale.ENGLISH));
1209                 break;
1210             case 1:
1211                 f = new DecimalFormat("#.#",
1212                             DecimalFormatSymbols.getInstance(Locale.ENGLISH));
1213                 f.applyPattern("");
1214                 break;
1215             }
1216             String s = f.format(123.456);
1217             if (!s.equals("123.456"))
1218                 fail("Fail: Format empty pattern x 123.456 => " + s);
1219             s = f.format(-123.456);
1220             if (!s.equals("-123.456"))
1221                 fail("Fail: Format empty pattern x -123.456 => " + s);
1222         }
1223     }
1224 
1225     /**
1226      * BigDecimal numbers get their fractions truncated by NumberFormat.
1227      */
1228     @Test
1229     public void Test4141750() {
1230         try {
1231             String str = "12345.67";
1232             BigDecimal bd = new BigDecimal(str);
1233             NumberFormat nf = NumberFormat.getInstance(Locale.US);
1234             String sd = nf.format(bd);
1235             if (!sd.endsWith("67")) {
1236                 fail("Fail: " + str + " x format -> " + sd);
1237             }
1238         }
1239         catch (Exception e) {
1240             fail(e.toString());
1241             e.printStackTrace();
1242         }
1243     }
1244 
1245     /**
1246      * DecimalFormat toPattern() doesn't quote special characters or handle
1247      * single quotes.
1248      */
1249     @Test
1250     public void Test4145457() {
1251         try {
1252             DecimalFormat nf = (DecimalFormat)NumberFormat.getInstance();
1253             DecimalFormatSymbols sym = nf.getDecimalFormatSymbols();
1254             sym.setDecimalSeparator('\'');
1255             nf.setDecimalFormatSymbols(sym);
1256             double pi = 3.14159;
1257 
1258             String[] PATS = { "#.00 'num''ber'", "''#.00''" };
1259 
1260             for (int i=0; i<PATS.length; ++i) {
1261                 nf.applyPattern(PATS[i]);
1262                 String out = nf.format(pi);
1263                 String pat = nf.toPattern();
1264                 double val = nf.parse(out).doubleValue();
1265 
1266                 nf.applyPattern(pat);
1267                 String out2 = nf.format(pi);
1268                 String pat2 = nf.toPattern();
1269                 double val2 = nf.parse(out2).doubleValue();
1270 
1271                 if (!pat.equals(pat2))
1272                     fail("Fail with \"" + PATS[i] + "\": Patterns should concur, \"" +
1273                           pat + "\" vs. \"" + pat2 + "\"");
1274                 else
1275                     System.out.println("Ok \"" + PATS[i] + "\" toPattern() -> \"" + pat + '"');
1276 
1277                 if (val == val2 && out.equals(out2)) {
1278                     System.out.println("Ok " + pi + " x \"" + PATS[i] + "\" -> \"" +
1279                           out + "\" -> " + val + " -> \"" +
1280                           out2 + "\" -> " + val2);
1281                 }
1282                 else {
1283                     fail("Fail " + pi + " x \"" + PATS[i] + "\" -> \"" +
1284                           out + "\" -> " + val + " -> \"" +
1285                           out2 + "\" -> " + val2);
1286                 }
1287             }
1288         }
1289         catch (ParseException e) {
1290             fail("Fail: " + e);
1291             e.printStackTrace();
1292         }
1293     }
1294 
1295     /**
1296      * DecimalFormat.applyPattern() sets minimum integer digits incorrectly.
1297      * CANNOT REPRODUCE
1298      * This bug is a duplicate of 4139344, which is a duplicate of 4134300
1299      */
1300     @Test
1301     public void Test4147295() {
1302         DecimalFormat sdf = new DecimalFormat();
1303         String pattern = "#,###";
1304         System.out.println("Applying pattern \"" + pattern + "\"");
1305         sdf.applyPattern(pattern);
1306         int minIntDig = sdf.getMinimumIntegerDigits();
1307         if (minIntDig != 0) {
1308             fail("Test failed"
1309             + "\n Minimum integer digits : " + minIntDig
1310             + "\n new pattern: " + sdf.toPattern());
1311         } else {
1312             System.out.println("Test passed");
1313             System.out.println(" Minimum integer digits : " + minIntDig);
1314         }
1315     }
1316 
1317     /**
1318      * DecimalFormat formats -0.0 as +0.0
1319      * See also older related bug 4106658, 4106667
1320      */
1321     @Test
1322     public void Test4147706() {
1323         DecimalFormat df = new DecimalFormat("#,##0.0##");
1324         df.setDecimalFormatSymbols(DecimalFormatSymbols.getInstance(Locale.ENGLISH));
1325         double d1 = -0.0;
1326         double d2 = -0.0001;
1327         StringBuffer f1 = df.format(d1, new StringBuffer(), new FieldPosition(0));
1328         StringBuffer f2 = df.format(d2, new StringBuffer(), new FieldPosition(0));
1329         if (!f1.toString().equals("-0.0")) {
1330             fail(d1 + " x \"" + df.toPattern() + "\" is formatted as \"" + f1 + '"');
1331         }
1332         if (!f2.toString().equals("-0.0")) {
1333             fail(d2 + " x \"" + df.toPattern() + "\" is formatted as \"" + f2 + '"');
1334         }
1335     }
1336 
1337     /**
1338      * NumberFormat cannot format Double.MAX_VALUE
1339      */
1340     @Test
1341     public void Test4162198() {
1342         double dbl = Double.MAX_VALUE;
1343         NumberFormat f = NumberFormat.getInstance();
1344         f.setMaximumFractionDigits(Integer.MAX_VALUE);
1345         f.setMaximumIntegerDigits(Integer.MAX_VALUE);
1346         String s = f.format(dbl);
1347         System.out.println("The number " + dbl + " formatted to " + s);
1348         Number n = null;
1349         try {
1350             n = f.parse(s);
1351         } catch (java.text.ParseException e) {
1352             fail("Caught a ParseException:");
1353             e.printStackTrace();
1354         }
1355         System.out.println("The string " + s + " parsed as " + n);
1356         if (n.doubleValue() != dbl) {
1357             fail("Round trip failure");
1358         }
1359     }
1360 
1361     /**
1362      * NumberFormat does not parse negative zero.
1363      */
1364     @Test
1365     public void Test4162852() throws ParseException {
1366         for (int i=0; i<2; ++i) {
1367             NumberFormat f = (i == 0) ? NumberFormat.getInstance()
1368                 : NumberFormat.getPercentInstance();
1369             double d = -0.0;
1370             String s = f.format(d);
1371             double e = f.parse(s).doubleValue();
1372             System.out.println("" +
1373                   d + " -> " +
1374                   '"' + s + '"' + " -> " +
1375               e);
1376             if (e != 0.0 || 1.0/e > 0.0) {
1377                 System.out.println("Failed to parse negative zero");
1378             }
1379         }
1380     }
1381 
1382     /**
1383      * NumberFormat truncates data
1384      */
1385     @Test
1386     public void Test4167494() throws Exception {
1387         NumberFormat fmt = NumberFormat.getInstance(Locale.US);
1388 
1389         double a = Double.MAX_VALUE;
1390         String s = fmt.format(a);
1391         double b = fmt.parse(s).doubleValue();
1392         boolean match = a == b;
1393         if (match) {
1394             System.out.println("" + a + " -> \"" + s + "\" -> " + b + " ok");
1395         } else {
1396             fail("" + a + " -> \"" + s + "\" -> " + b + " FAIL");
1397         }
1398 
1399         // We don't test Double.MIN_VALUE because the locale data for the US
1400         // currently doesn't specify enough digits to display Double.MIN_VALUE.
1401         // This is correct for now; however, we leave this here as a reminder
1402         // in case we want to address this later.
1403         if (false) {
1404             a = Double.MIN_VALUE;
1405             s = fmt.format(a);
1406             b = fmt.parse(s).doubleValue();
1407             match = a == b;
1408             if (match) {
1409                 System.out.println("" + a + " -> \"" + s + "\" -> " + b + " ok");
1410             } else {
1411                 fail("" + a + " -> \"" + s + "\" -> " + b + " FAIL");
1412             }
1413         }
1414     }
1415 
1416     /**
1417      * DecimalFormat.parse() fails when ParseIntegerOnly set to true
1418      */
1419     @Test
1420     public void Test4170798() {
1421         Locale savedLocale = Locale.getDefault();
1422         Locale.setDefault(Locale.US);
1423         DecimalFormat df = new DecimalFormat();
1424         df.setParseIntegerOnly(true);
1425         Number n = df.parse("-0.0", new ParsePosition(0));
1426         if (!(n instanceof Long || n instanceof Integer)
1427             || n.intValue() != 0) {
1428             fail("FAIL: parse(\"-0.0\") returns " +
1429                   n + " (" + n.getClass().getName() + ')');
1430         }
1431         Locale.setDefault(savedLocale);
1432     }
1433 
1434     /**
1435      * toPattern only puts the first grouping separator in.
1436      */
1437     @Test
1438     public void Test4176114() {
1439         String[] DATA = {
1440             "00", "#00",
1441             "000", "#000", // No grouping
1442             "#000", "#000", // No grouping
1443             "#,##0", "#,##0",
1444             "#,000", "#,000",
1445             "0,000", "#0,000",
1446             "00,000", "#00,000",
1447             "000,000", "#,000,000",
1448             "0,000,000,000,000.0000", "#0,000,000,000,000.0000", // Reported
1449         };
1450         for (int i=0; i<DATA.length; i+=2) {
1451             DecimalFormat df = new DecimalFormat(DATA[i]);
1452             String s = df.toPattern();
1453             if (!s.equals(DATA[i+1])) {
1454                 fail("FAIL: " + DATA[i] + " -> " + s + ", want " + DATA[i+1]);
1455             }
1456         }
1457     }
1458 
1459     /**
1460      * DecimalFormat is incorrectly rounding numbers like 1.2501 to 1.2
1461      */
1462     @Test
1463     public void Test4179818() {
1464         String DATA[] = {
1465             // Input  Pattern  Expected output
1466             "1.2511", "#.#",   "1.3",
1467             "1.2501", "#.#",   "1.3",
1468             "0.9999", "#",     "1",
1469         };
1470         DecimalFormat fmt = new DecimalFormat("#",
1471                 DecimalFormatSymbols.getInstance(Locale.US));
1472         for (int i=0; i<DATA.length; i+=3) {
1473             double in = Double.valueOf(DATA[i]);
1474             String pat = DATA[i+1];
1475             String exp = DATA[i+2];
1476             fmt.applyPattern(pat);
1477             String out = fmt.format(in);
1478             if (out.equals(exp)) {
1479                 System.out.println("Ok: " + in + " x " + pat + " = " + out);
1480             } else {
1481                 fail("FAIL: " + in + " x  " + pat + " = " + out +
1482                       ", expected " + exp);
1483             }
1484         }
1485     }
1486 
1487     @Test
1488     public void Test4185761() throws IOException, ClassNotFoundException {
1489         /* Code used to write out the initial files, which are
1490          * then edited manually:
1491         NumberFormat nf = NumberFormat.getInstance(Locale.US);
1492         nf.setMinimumIntegerDigits(0x111); // Keep under 309
1493         nf.setMaximumIntegerDigits(0x112); // Keep under 309
1494         nf.setMinimumFractionDigits(0x113); // Keep under 340
1495         nf.setMaximumFractionDigits(0x114); // Keep under 340
1496         FileOutputStream ostream =
1497             new FileOutputStream("NumberFormat4185761");
1498         ObjectOutputStream p = new ObjectOutputStream(ostream);
1499         p.writeObject(nf);
1500         ostream.close();
1501         */
1502 
1503         // File                 minint maxint minfrac maxfrac
1504         // NumberFormat4185761a  0x122  0x121   0x124   0x123
1505         // NumberFormat4185761b  0x311  0x312   0x313   0x314
1506         // File a is bad because the mins are smaller than the maxes.
1507         // File b is bad because the values are too big for a DecimalFormat.
1508         // These files have a sufix ".ser.txt".
1509 
1510         InputStream istream = HexDumpReader.getStreamFromHexDump("NumberFormat4185761a.ser.txt");
1511         ObjectInputStream p = new ObjectInputStream(istream);
1512         try {
1513             NumberFormat nf = (NumberFormat) p.readObject();
1514             fail("FAIL: Deserialized bogus NumberFormat int:" +
1515                   nf.getMinimumIntegerDigits() + ".." +
1516                   nf.getMaximumIntegerDigits() + " frac:" +
1517                   nf.getMinimumFractionDigits() + ".." +
1518                   nf.getMaximumFractionDigits());
1519         } catch (InvalidObjectException e) {
1520             System.out.println("Ok: " + e.getMessage());
1521         }
1522         istream.close();
1523 
1524         istream = HexDumpReader.getStreamFromHexDump("NumberFormat4185761b.ser.txt");
1525         p = new ObjectInputStream(istream);
1526         try {
1527             NumberFormat nf = (NumberFormat) p.readObject();
1528             fail("FAIL: Deserialized bogus DecimalFormat int:" +
1529                   nf.getMinimumIntegerDigits() + ".." +
1530                   nf.getMaximumIntegerDigits() + " frac:" +
1531                   nf.getMinimumFractionDigits() + ".." +
1532                   nf.getMaximumFractionDigits());
1533         } catch (InvalidObjectException e) {
1534             System.out.println("Ok: " + e.getMessage());
1535         }
1536         istream.close();
1537     }
1538 
1539 
1540     /**
1541      * Some DecimalFormatSymbols changes are not picked up by DecimalFormat.
1542      * This includes the minus sign, currency symbol, international currency
1543      * symbol, percent, and permille.  This is filed as bugs 4212072 and
1544      * 4212073.
1545      */
1546     @Test
1547     public void Test4212072() throws IOException, ClassNotFoundException {
1548         DecimalFormatSymbols sym = DecimalFormatSymbols.getInstance(Locale.US);
1549         DecimalFormat fmt = new DecimalFormat("#", sym);
1550 
1551         sym.setMinusSign('^');
1552         fmt.setDecimalFormatSymbols(sym);
1553         if (!fmt.format(-1).equals("^1")) {
1554             fail("FAIL: -1 x (minus=^) -> " + fmt.format(-1) +
1555                   ", exp ^1");
1556         }
1557         if (!fmt.getNegativePrefix().equals("^")) {
1558             fail("FAIL: (minus=^).getNegativePrefix -> " +
1559                   fmt.getNegativePrefix() + ", exp ^");
1560         }
1561         sym.setMinusSign('-');
1562 
1563         fmt.applyPattern("#%");
1564         sym.setPercent('^');
1565         fmt.setDecimalFormatSymbols(sym);
1566         if (!fmt.format(0.25).equals("25^")) {
1567             fail("FAIL: 0.25 x (percent=^) -> " + fmt.format(0.25) +
1568                   ", exp 25^");
1569         }
1570         if (!fmt.getPositiveSuffix().equals("^")) {
1571             fail("FAIL: (percent=^).getPositiveSuffix -> " +
1572                   fmt.getPositiveSuffix() + ", exp ^");
1573         }
1574         sym.setPercent('%');
1575 
1576         fmt.applyPattern("#\u2030");
1577         sym.setPerMill('^');
1578         fmt.setDecimalFormatSymbols(sym);
1579         if (!fmt.format(0.25).equals("250^")) {
1580             fail("FAIL: 0.25 x (permill=^) -> " + fmt.format(0.25) +
1581                   ", exp 250^");
1582         }
1583         if (!fmt.getPositiveSuffix().equals("^")) {
1584             fail("FAIL: (permill=^).getPositiveSuffix -> " +
1585                   fmt.getPositiveSuffix() + ", exp ^");
1586         }
1587         sym.setPerMill('\u2030');
1588 
1589         fmt.applyPattern("\u00A4#.00");
1590         sym.setCurrencySymbol("usd");
1591         fmt.setDecimalFormatSymbols(sym);
1592         if (!fmt.format(12.5).equals("usd12.50")) {
1593             fail("FAIL: 12.5 x (currency=usd) -> " + fmt.format(12.5) +
1594                   ", exp usd12.50");
1595         }
1596         if (!fmt.getPositivePrefix().equals("usd")) {
1597             fail("FAIL: (currency=usd).getPositivePrefix -> " +
1598                   fmt.getPositivePrefix() + ", exp usd");
1599         }
1600         sym.setCurrencySymbol("$");
1601 
1602         fmt.applyPattern("\u00A4\u00A4#.00");
1603         sym.setInternationalCurrencySymbol("DOL");
1604         fmt.setDecimalFormatSymbols(sym);
1605         if (!fmt.format(12.5).equals("DOL12.50")) {
1606             fail("FAIL: 12.5 x (intlcurrency=DOL) -> " + fmt.format(12.5) +
1607                   ", exp DOL12.50");
1608         }
1609         if (!fmt.getPositivePrefix().equals("DOL")) {
1610             fail("FAIL: (intlcurrency=DOL).getPositivePrefix -> " +
1611                   fmt.getPositivePrefix() + ", exp DOL");
1612         }
1613         sym.setInternationalCurrencySymbol("USD");
1614 
1615         // Since the pattern logic has changed, make sure that patterns round
1616         // trip properly.  Test stream in/out integrity too.
1617         Locale[] avail = NumberFormat.getAvailableLocales();
1618         for (int i=0; i<avail.length; ++i) {
1619             for (int j=0; j<3; ++j) {
1620                 NumberFormat nf;
1621                 switch (j) {
1622                 case 0:
1623                     nf = NumberFormat.getInstance(avail[i]);
1624                     break;
1625                 case 1:
1626                     nf = NumberFormat.getCurrencyInstance(avail[i]);
1627                     break;
1628                 default:
1629                     nf = NumberFormat.getPercentInstance(avail[i]);
1630                     break;
1631                 }
1632                 DecimalFormat df = (DecimalFormat) nf;
1633 
1634                 // Test toPattern/applyPattern round trip
1635                 String pat = df.toPattern();
1636                 DecimalFormatSymbols symb = DecimalFormatSymbols.getInstance(avail[i]);
1637                 DecimalFormat f2 = new DecimalFormat(pat, symb);
1638                 if (!df.equals(f2)) {
1639                     fail("FAIL: " + avail[i] + " -> \"" + pat +
1640                           "\" -> \"" + f2.toPattern() + '"');
1641                 }
1642 
1643                 // Test toLocalizedPattern/applyLocalizedPattern round trip
1644                 pat = df.toLocalizedPattern();
1645                 f2.applyLocalizedPattern(pat);
1646                 if (!df.equals(f2)) {
1647                     fail("FAIL: " + avail[i] + " -> localized \"" + pat +
1648                           "\" -> \"" + f2.toPattern() + '"');
1649                 }
1650 
1651                 // Test writeObject/readObject round trip
1652                 ByteArrayOutputStream baos = new ByteArrayOutputStream();
1653                 ObjectOutputStream oos = new ObjectOutputStream(baos);
1654                 oos.writeObject(df);
1655                 oos.flush();
1656                 baos.close();
1657                 byte[] bytes = baos.toByteArray();
1658                 ObjectInputStream ois =
1659                     new ObjectInputStream(new ByteArrayInputStream(bytes));
1660                 f2 = (DecimalFormat) ois.readObject();
1661                 if (!df.equals(f2)) {
1662                     fail("FAIL: Stream in/out " + avail[i] + " -> \"" + pat +
1663                           "\" -> " +
1664                           (f2 != null ? ("\""+f2.toPattern()+'"') : "null"));
1665                 }
1666 
1667             }
1668         }
1669     }
1670 
1671     /**
1672      * DecimalFormat.parse() fails for mulipliers 2^n.
1673      */
1674     @Test
1675     public void Test4216742() throws ParseException {
1676         DecimalFormat fmt = (DecimalFormat) NumberFormat.getInstance(Locale.US);
1677         long[] DATA = { Long.MIN_VALUE, Long.MAX_VALUE, -100000000L, 100000000L};
1678         for (int i=0; i<DATA.length; ++i) {
1679             String str = Long.toString(DATA[i]);
1680             for (int m = 1; m <= 100; m++) {
1681                 fmt.setMultiplier(m);
1682                 long n = fmt.parse(str).longValue();
1683                 if (n > 0 != DATA[i] > 0) {
1684                     fail("\"" + str + "\" parse(x " + fmt.getMultiplier() +
1685                           ") => " + n);
1686                 }
1687             }
1688         }
1689     }
1690 
1691     /**
1692      * DecimalFormat formats 1.001 to "1.00" instead of "1" with 2 fraction
1693      * digits.
1694      */
1695     @Test
1696     public void Test4217661() {
1697         Object[] DATA = {
1698             0.001, "0",
1699             1.001, "1",
1700             0.006, "0.01",
1701             1.006, "1.01",
1702         };
1703         NumberFormat fmt = NumberFormat.getInstance(Locale.US);
1704         fmt.setMaximumFractionDigits(2);
1705         for (int i=0; i<DATA.length; i+=2) {
1706             String s = fmt.format((Double) DATA[i]);
1707             if (!s.equals(DATA[i+1])) {
1708                 fail("FAIL: Got " + s + ", exp " + DATA[i+1]);
1709             }
1710         }
1711     }
1712 
1713     /**
1714      * 4243011: Formatting .5 rounds to "1" instead of "0"
1715      */
1716     @Test
1717     public void Test4243011() {
1718         Locale savedLocale = Locale.getDefault();
1719         Locale.setDefault(Locale.US);
1720         double DATA[] = {0.5, 1.5, 2.5, 3.5, 4.5};
1721         String EXPECTED[] = {"0.", "2.", "2.", "4.", "4."};
1722 
1723         DecimalFormat format = new DecimalFormat("0.");
1724         for (int i = 0; i < DATA.length; i++) {
1725             String result = format.format(DATA[i]);
1726             if (result.equals(EXPECTED[i])) {
1727                 System.out.println("OK: got " + result);
1728             } else {
1729                 fail("FAIL: got " + result);
1730             }
1731         }
1732         Locale.setDefault(savedLocale);
1733     }
1734 
1735     /**
1736      * 4243108: format(0.0) gives "0.1" if preceded by parse("99.99")
1737      */
1738     @Test
1739     public void Test4243108() {
1740         Locale savedLocale = Locale.getDefault();
1741         Locale.setDefault(Locale.US);
1742         DecimalFormat f = new DecimalFormat("#.#");
1743         String result = f.format(0.0);
1744         if (result.equals("0")) {
1745             System.out.println("OK: got " + result);
1746         } else {
1747             fail("FAIL: got " + result);
1748         }
1749         try {
1750             double dResult = f.parse("99.99").doubleValue();
1751             if (dResult == 99.99) {
1752                 System.out.println("OK: got " + dResult);
1753             } else {
1754                 fail("FAIL: got " + dResult);
1755             }
1756         } catch (ParseException e) {
1757             fail("Caught a ParseException:");
1758             e.printStackTrace();
1759         }
1760         result = f.format(0.0);
1761         if (result.equals("0")) {
1762             System.out.println("OK: got " + result);
1763         } else {
1764             fail("FAIL: got " + result);
1765         }
1766         Locale.setDefault(savedLocale);
1767     }
1768 
1769     /**
1770      * 4330377: DecimalFormat engineering notation gives incorrect results
1771      */
1772     @Test
1773     public void test4330377() {
1774         Locale savedLocale = Locale.getDefault();
1775         Locale.setDefault(Locale.US);
1776         double[] input = {5000.0, 500.0, 50.0, 5.0, 0.5, 0.05, 0.005, 0.0005,
1777                5050.0, 505.0, 50.5, 5.05, 0.505, 0.0505, 0.00505, 0.000505};
1778         String[] pattern = {"000.#E0", "##0.#E0", "#00.#E0"};
1779         String[][] expected = {
1780             // it's questionable whether "#00.#E0" should result in post-decimal
1781             // zeroes, i.e., whether "5.0E3", "5.0E0", "5.0E-3" are really good
1782             {"500E1", "5E3", "5.0E3"},
1783             {"500E0", "500E0", "500E0"},
1784             {"500E-1", "50E0", "50E0"},
1785             {"500E-2", "5E0", "5.0E0"},
1786             {"500E-3", "500E-3", "500E-3"},
1787             {"500E-4", "50E-3", "50E-3"},
1788             {"500E-5", "5E-3", "5.0E-3"},
1789             {"500E-6", "500E-6", "500E-6"},
1790             {"505E1", "5.05E3", "5.05E3"},
1791             {"505E0", "505E0", "505E0"},
1792             {"505E-1", "50.5E0", "50.5E0"},
1793             {"505E-2", "5.05E0", "5.05E0"},
1794             {"505E-3", "505E-3", "505E-3"},
1795             {"505E-4", "50.5E-3", "50.5E-3"},
1796             {"505E-5", "5.05E-3", "5.05E-3"},
1797             {"505E-6", "505E-6", "505E-6"}
1798         };
1799         for (int i = 0; i < input.length; i++) {
1800             for (int j = 0; j < pattern.length; j++) {
1801                 DecimalFormat format = new DecimalFormat(pattern[j]);
1802                 String result = format.format(input[i]);
1803                 if (!result.equals(expected[i][j])) {
1804                     fail("FAIL: input: " + input[i] +
1805                             ", pattern: " + pattern[j] +
1806                             ", expected: " + expected[i][j] +
1807                             ", got: " + result);
1808                 }
1809             }
1810         }
1811         Locale.setDefault(savedLocale);
1812     }
1813 
1814     /**
1815      * 4233840: NumberFormat does not round correctly
1816      */
1817     @Test
1818     public void test4233840() {
1819         float f = 0.0099f;
1820 
1821         NumberFormat nf = new DecimalFormat("0.##", DecimalFormatSymbols.getInstance(Locale.US));
1822         nf.setMinimumFractionDigits(2);
1823 
1824         String result = nf.format(f);
1825 
1826         if (!result.equals("0.01")) {
1827             fail("FAIL: input: " + f + ", expected: 0.01, got: " + result);
1828         }
1829     }
1830 
1831     /**
1832      * 4241880: Decimal format doesnt round a double properly when the number is less than 1
1833      */
1834     @Test
1835     public void test4241880() {
1836         Locale savedLocale = Locale.getDefault();
1837         Locale.setDefault(Locale.US);
1838         double[] input = {
1839                 .019, .009, .015, .016, .014,
1840                 .004, .005, .006, .007, .008,
1841                 .5, 1.5, .25, .55, .045,
1842                 .035, .0005, .0015,
1843         };
1844         String[] pattern = {
1845                 "##0%", "##0%", "##0%", "##0%", "##0%",
1846                 "##0%", "##0%", "##0%", "##0%", "##0%",
1847                 "#,##0", "#,##0", "#,##0.0", "#,##0.0", "#,##0.00",
1848                 "#,##0.00", "#,##0.000", "#,##0.000",
1849         };
1850         String[] expected = {
1851                 "2%", "1%", "2%", "2%", "1%",
1852                 "0%", "0%", "1%", "1%", "1%",
1853                 "0", "2", "0.2", "0.6", "0.04",
1854                 "0.04", "0.000", "0.002",
1855         };
1856         for (int i = 0; i < input.length; i++) {
1857             DecimalFormat format = new DecimalFormat(pattern[i]);
1858             String result = format.format(input[i]);
1859             if (!result.equals(expected[i])) {
1860                 fail("FAIL: input: " + input[i] +
1861                         ", pattern: " + pattern[i] +
1862                         ", expected: " + expected[i] +
1863                         ", got: " + result);
1864             }
1865         }
1866         Locale.setDefault(savedLocale);
1867     }
1868 
1869     /**
1870      * Test for get/setMonetaryGroupingSeparator() methods.
1871      * @since 15
1872      */
1873     @Test
1874     public void test8227313() throws ParseException {
1875         var nrmSep = 'n';
1876         var monSep = 'm';
1877         var curSym = "Cur";
1878         var inputNum = 10;
1879         var nrmPattern = ",#";
1880         var monPattern = "\u00a4 ,#";
1881         var expectedNrmFmt = "1n0";
1882         var expectedMonFmt = "Cur 1m0";
1883 
1884         var ndfs = DecimalFormatSymbols.getInstance();
1885         ndfs.setGroupingSeparator(nrmSep);
1886         var nf = new DecimalFormat(nrmPattern, ndfs);
1887         var mdfs = DecimalFormatSymbols.getInstance();
1888         mdfs.setMonetaryGroupingSeparator(monSep);
1889         mdfs.setCurrencySymbol(curSym);
1890         var mf = new DecimalFormat(monPattern, mdfs);
1891 
1892         // get test
1893         char gotNrmSep = mdfs.getGroupingSeparator();
1894         char gotMonSep = mdfs.getMonetaryGroupingSeparator();
1895         if (gotMonSep != monSep) {
1896             fail("FAIL: getMonetaryGroupingSeparator() returned incorrect value. expected: "
1897                     + monSep + ", got: " + gotMonSep);
1898         }
1899         if (gotMonSep == gotNrmSep) {
1900             fail("FAIL: getMonetaryGroupingSeparator() returned the same value with " +
1901                     "getGroupingSeparator(): monetary sep: " + gotMonSep +
1902                     ", normal sep: " + gotNrmSep);
1903         }
1904 
1905         // format test
1906         var formatted = mf.format(inputNum);
1907         if (!formatted.equals(expectedMonFmt)) {
1908             fail("FAIL: format failed. expected: " + expectedMonFmt +
1909                     ", got: " + formatted);
1910         }
1911         formatted = nf.format(inputNum);
1912         if (!formatted.equals(expectedNrmFmt)) {
1913             fail("FAIL: normal format failed. expected: " + expectedNrmFmt +
1914                     ", got: " + formatted);
1915         }
1916 
1917         // parse test
1918         Number parsed = mf.parse(expectedMonFmt);
1919         if (parsed.intValue() != inputNum) {
1920             fail("FAIL: parse failed. expected: " + inputNum +
1921                     ", got: " + parsed);
1922         }
1923         parsed = nf.parse(expectedNrmFmt);
1924         if (parsed.intValue() != inputNum) {
1925             fail("FAIL: normal parse failed. expected: " + inputNum +
1926                     ", got: " + parsed);
1927         }
1928     }
1929 }
1930 
1931 @SuppressWarnings("serial")
1932 class myformat implements Serializable
1933 {
1934     DateFormat _dateFormat = DateFormat.getDateInstance();
1935 
1936     public String Now()
1937     {
1938         GregorianCalendar calendar = new GregorianCalendar();
1939         Date t = calendar.getTime();
1940         String nowStr = _dateFormat.format(t);
1941         return nowStr;
1942     }
1943 }
1944 
1945 @SuppressWarnings("serial")
1946 class MyNumberFormatTest extends NumberFormat {
1947     public StringBuffer format(double number, StringBuffer toAppendTo, FieldPosition pos) {
1948         return new StringBuffer("");
1949     }
1950     public StringBuffer format(long number,StringBuffer toAppendTo, FieldPosition pos) {
1951         return new StringBuffer("");
1952     }
1953     public Number parse(String text, ParsePosition parsePosition) {
1954         return 0;
1955     }
1956 }