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 package java.io;
  27 
  28 import java.util.Objects;
  29 import java.util.Formatter;
  30 import java.util.Locale;
  31 import java.nio.charset.Charset;
  32 import java.nio.charset.IllegalCharsetNameException;
  33 import java.nio.charset.UnsupportedCharsetException;
  34 
  35 /**
  36  * Prints formatted representations of objects to a text-output stream.  This
  37  * class implements all of the <tt>print</tt> methods found in {@link
  38  * PrintStream}.  It does not contain methods for writing raw bytes, for which
  39  * a program should use unencoded byte streams.
  40  *
  41  * <p> Unlike the {@link PrintStream} class, if automatic flushing is enabled
  42  * it will be done only when one of the <tt>println</tt>, <tt>printf</tt>, or
  43  * <tt>format</tt> methods is invoked, rather than whenever a newline character
  44  * happens to be output.  These methods use the platform's own notion of line
  45  * separator rather than the newline character.
  46  *
  47  * <p> Methods in this class never throw I/O exceptions, although some of its
  48  * constructors may.  The client may inquire as to whether any errors have
  49  * occurred by invoking {@link #checkError checkError()}.
  50  *
  51  * @author      Frank Yellin
  52  * @author      Mark Reinhold
  53  * @since       1.1
  54  */
  55 
  56 public class PrintWriter extends Writer {
  57 
  58     /**
  59      * The underlying character-output stream of this
  60      * <code>PrintWriter</code>.
  61      *
  62      * @since 1.2
  63      */
  64     protected Writer out;
  65 
  66     private final boolean autoFlush;
  67     private boolean trouble = false;
  68     private Formatter formatter;
  69     private PrintStream psOut = null;
  70 
  71     /**
  72      * Returns a charset object for the given charset name.
  73      * @throws NullPointerException          is csn is null
  74      * @throws UnsupportedEncodingException  if the charset is not supported
  75      */
  76     private static Charset toCharset(String csn)
  77         throws UnsupportedEncodingException
  78     {
  79         Objects.requireNonNull(csn, "charsetName");
  80         try {
  81             return Charset.forName(csn);
  82         } catch (IllegalCharsetNameException|UnsupportedCharsetException unused) {
  83             // UnsupportedEncodingException should be thrown
  84             throw new UnsupportedEncodingException(csn);
  85         }
  86     }
  87 
  88     /**
  89      * Creates a new PrintWriter, without automatic line flushing.
  90      *
  91      * @param  out        A character-output stream
  92      */
  93     public PrintWriter (Writer out) {
  94         this(out, false);
  95     }
  96 
  97     /**
  98      * Creates a new PrintWriter.
  99      *
 100      * @param  out        A character-output stream
 101      * @param  autoFlush  A boolean; if true, the <tt>println</tt>,
 102      *                    <tt>printf</tt>, or <tt>format</tt> methods will
 103      *                    flush the output buffer
 104      */
 105     public PrintWriter(Writer out,
 106                        boolean autoFlush) {
 107         super(out);
 108         this.out = out;
 109         this.autoFlush = autoFlush;
 110     }
 111 
 112     /**
 113      * Creates a new PrintWriter, without automatic line flushing, from an
 114      * existing OutputStream.  This convenience constructor creates the
 115      * necessary intermediate OutputStreamWriter, which will convert characters
 116      * into bytes using the default character encoding.
 117      *
 118      * @param  out        An output stream
 119      *
 120      * @see java.io.OutputStreamWriter#OutputStreamWriter(java.io.OutputStream)
 121      */
 122     public PrintWriter(OutputStream out) {
 123         this(out, false);
 124     }
 125 
 126     /**
 127      * Creates a new PrintWriter from an existing OutputStream.  This
 128      * convenience constructor creates the necessary intermediate
 129      * OutputStreamWriter, which will convert characters into bytes using the
 130      * default character encoding.
 131      *
 132      * @param  out        An output stream
 133      * @param  autoFlush  A boolean; if true, the <tt>println</tt>,
 134      *                    <tt>printf</tt>, or <tt>format</tt> methods will
 135      *                    flush the output buffer
 136      *
 137      * @see java.io.OutputStreamWriter#OutputStreamWriter(java.io.OutputStream)
 138      */
 139     public PrintWriter(OutputStream out, boolean autoFlush) {
 140         this(new BufferedWriter(new OutputStreamWriter(out)), autoFlush);
 141 
 142         // save print stream for error propagation
 143         if (out instanceof java.io.PrintStream) {
 144             psOut = (PrintStream) out;
 145         }
 146     }
 147 
 148     /**
 149      * Creates a new PrintWriter, without automatic line flushing, with the
 150      * specified file name.  This convenience constructor creates the necessary
 151      * intermediate {@link java.io.OutputStreamWriter OutputStreamWriter},
 152      * which will encode characters using the {@linkplain
 153      * java.nio.charset.Charset#defaultCharset() default charset} for this
 154      * instance of the Java virtual machine.
 155      *
 156      * @param  fileName
 157      *         The name of the file to use as the destination of this writer.
 158      *         If the file exists then it will be truncated to zero size;
 159      *         otherwise, a new file will be created.  The output will be
 160      *         written to the file and is buffered.
 161      *
 162      * @throws  FileNotFoundException
 163      *          If the given string does not denote an existing, writable
 164      *          regular file and a new regular file of that name cannot be
 165      *          created, or if some other error occurs while opening or
 166      *          creating the file
 167      *
 168      * @throws  SecurityException
 169      *          If a security manager is present and {@link
 170      *          SecurityManager#checkWrite checkWrite(fileName)} denies write
 171      *          access to the file
 172      *
 173      * @since  1.5
 174      */
 175     public PrintWriter(String fileName) throws FileNotFoundException {
 176         this(new BufferedWriter(new OutputStreamWriter(new FileOutputStream(fileName))),
 177              false);
 178     }
 179 
 180     /* Private constructor */
 181     private PrintWriter(Charset charset, File file)
 182         throws FileNotFoundException
 183     {
 184         this(new BufferedWriter(new OutputStreamWriter(new FileOutputStream(file), charset)),
 185              false);
 186     }
 187 
 188     /**
 189      * Creates a new PrintWriter, without automatic line flushing, with the
 190      * specified file name and charset.  This convenience constructor creates
 191      * the necessary intermediate {@link java.io.OutputStreamWriter
 192      * OutputStreamWriter}, which will encode characters using the provided
 193      * charset.
 194      *
 195      * @param  fileName
 196      *         The name of the file to use as the destination of this writer.
 197      *         If the file exists then it will be truncated to zero size;
 198      *         otherwise, a new file will be created.  The output will be
 199      *         written to the file and is buffered.
 200      *
 201      * @param  csn
 202      *         The name of a supported {@linkplain java.nio.charset.Charset
 203      *         charset}
 204      *
 205      * @throws  FileNotFoundException
 206      *          If the given string does not denote an existing, writable
 207      *          regular file and a new regular file of that name cannot be
 208      *          created, or if some other error occurs while opening or
 209      *          creating the file
 210      *
 211      * @throws  SecurityException
 212      *          If a security manager is present and {@link
 213      *          SecurityManager#checkWrite checkWrite(fileName)} denies write
 214      *          access to the file
 215      *
 216      * @throws  UnsupportedEncodingException
 217      *          If the named charset is not supported
 218      *
 219      * @since  1.5
 220      */
 221     public PrintWriter(String fileName, String csn)
 222         throws FileNotFoundException, UnsupportedEncodingException
 223     {
 224         this(toCharset(csn), new File(fileName));
 225     }
 226 
 227     /**
 228      * Creates a new PrintWriter, without automatic line flushing, with the
 229      * specified file.  This convenience constructor creates the necessary
 230      * intermediate {@link java.io.OutputStreamWriter OutputStreamWriter},
 231      * which will encode characters using the {@linkplain
 232      * java.nio.charset.Charset#defaultCharset() default charset} for this
 233      * instance of the Java virtual machine.
 234      *
 235      * @param  file
 236      *         The file to use as the destination of this writer.  If the file
 237      *         exists then it will be truncated to zero size; otherwise, a new
 238      *         file will be created.  The output will be written to the file
 239      *         and is buffered.
 240      *
 241      * @throws  FileNotFoundException
 242      *          If the given file object does not denote an existing, writable
 243      *          regular file and a new regular file of that name cannot be
 244      *          created, or if some other error occurs while opening or
 245      *          creating the file
 246      *
 247      * @throws  SecurityException
 248      *          If a security manager is present and {@link
 249      *          SecurityManager#checkWrite checkWrite(file.getPath())}
 250      *          denies write access to the file
 251      *
 252      * @since  1.5
 253      */
 254     public PrintWriter(File file) throws FileNotFoundException {
 255         this(new BufferedWriter(new OutputStreamWriter(new FileOutputStream(file))),
 256              false);
 257     }
 258 
 259     /**
 260      * Creates a new PrintWriter, without automatic line flushing, with the
 261      * specified file and charset.  This convenience constructor creates the
 262      * necessary intermediate {@link java.io.OutputStreamWriter
 263      * OutputStreamWriter}, which will encode characters using the provided
 264      * charset.
 265      *
 266      * @param  file
 267      *         The file to use as the destination of this writer.  If the file
 268      *         exists then it will be truncated to zero size; otherwise, a new
 269      *         file will be created.  The output will be written to the file
 270      *         and is buffered.
 271      *
 272      * @param  csn
 273      *         The name of a supported {@linkplain java.nio.charset.Charset
 274      *         charset}
 275      *
 276      * @throws  FileNotFoundException
 277      *          If the given file object does not denote an existing, writable
 278      *          regular file and a new regular file of that name cannot be
 279      *          created, or if some other error occurs while opening or
 280      *          creating the file
 281      *
 282      * @throws  SecurityException
 283      *          If a security manager is present and {@link
 284      *          SecurityManager#checkWrite checkWrite(file.getPath())}
 285      *          denies write access to the file
 286      *
 287      * @throws  UnsupportedEncodingException
 288      *          If the named charset is not supported
 289      *
 290      * @since  1.5
 291      */
 292     public PrintWriter(File file, String csn)
 293         throws FileNotFoundException, UnsupportedEncodingException
 294     {
 295         this(toCharset(csn), file);
 296     }
 297 
 298     /** Checks to make sure that the stream has not been closed */
 299     private void ensureOpen() throws IOException {
 300         if (out == null)
 301             throw new IOException("Stream closed");
 302     }
 303 
 304     /**
 305      * Flushes the stream.
 306      * @see #checkError()
 307      */
 308     public void flush() {
 309         try {
 310             synchronized (lock) {
 311                 ensureOpen();
 312                 out.flush();
 313             }
 314         }
 315         catch (IOException x) {
 316             trouble = true;
 317         }
 318     }
 319 
 320     /**
 321      * Closes the stream and releases any system resources associated
 322      * with it. Closing a previously closed stream has no effect.
 323      *
 324      * @see #checkError()
 325      */
 326     public void close() {
 327         try {
 328             synchronized (lock) {
 329                 if (out == null)
 330                     return;
 331                 out.close();
 332                 out = null;
 333             }
 334         }
 335         catch (IOException x) {
 336             trouble = true;
 337         }
 338     }
 339 
 340     /**
 341      * Flushes the stream if it's not closed and checks its error state.
 342      *
 343      * @return <code>true</code> if the print stream has encountered an error,
 344      *          either on the underlying output stream or during a format
 345      *          conversion.
 346      */
 347     public boolean checkError() {
 348         if (out != null) {
 349             flush();
 350         }
 351         if (out instanceof java.io.PrintWriter) {
 352             PrintWriter pw = (PrintWriter) out;
 353             return pw.checkError();
 354         } else if (psOut != null) {
 355             return psOut.checkError();
 356         }
 357         return trouble;
 358     }
 359 
 360     /**
 361      * Indicates that an error has occurred.
 362      *
 363      * <p> This method will cause subsequent invocations of {@link
 364      * #checkError()} to return <tt>true</tt> until {@link
 365      * #clearError()} is invoked.
 366      */
 367     protected void setError() {
 368         trouble = true;
 369     }
 370 
 371     /**
 372      * Clears the error state of this stream.
 373      *
 374      * <p> This method will cause subsequent invocations of {@link
 375      * #checkError()} to return <tt>false</tt> until another write
 376      * operation fails and invokes {@link #setError()}.
 377      *
 378      * @since 1.6
 379      */
 380     protected void clearError() {
 381         trouble = false;
 382     }
 383 
 384     /*
 385      * Exception-catching, synchronized output operations,
 386      * which also implement the write() methods of Writer
 387      */
 388 
 389     /**
 390      * Writes a single character.
 391      * @param c int specifying a character to be written.
 392      */
 393     public void write(int c) {
 394         try {
 395             synchronized (lock) {
 396                 ensureOpen();
 397                 out.write(c);
 398             }
 399         }
 400         catch (InterruptedIOException x) {
 401             Thread.currentThread().interrupt();
 402         }
 403         catch (IOException x) {
 404             trouble = true;
 405         }
 406     }
 407 
 408     /**
 409      * Writes A Portion of an array of characters.
 410      * @param buf Array of characters
 411      * @param off Offset from which to start writing characters
 412      * @param len Number of characters to write
 413      */
 414     public void write(char buf[], int off, int len) {
 415         try {
 416             synchronized (lock) {
 417                 ensureOpen();
 418                 out.write(buf, off, len);
 419             }
 420         }
 421         catch (InterruptedIOException x) {
 422             Thread.currentThread().interrupt();
 423         }
 424         catch (IOException x) {
 425             trouble = true;
 426         }
 427     }
 428 
 429     /**
 430      * Writes an array of characters.  This method cannot be inherited from the
 431      * Writer class because it must suppress I/O exceptions.
 432      * @param buf Array of characters to be written
 433      */
 434     public void write(char buf[]) {
 435         write(buf, 0, buf.length);
 436     }
 437 
 438     /**
 439      * Writes a portion of a string.
 440      * @param s A String
 441      * @param off Offset from which to start writing characters
 442      * @param len Number of characters to write
 443      */
 444     public void write(String s, int off, int len) {
 445         try {
 446             synchronized (lock) {
 447                 ensureOpen();
 448                 out.write(s, off, len);
 449             }
 450         }
 451         catch (InterruptedIOException x) {
 452             Thread.currentThread().interrupt();
 453         }
 454         catch (IOException x) {
 455             trouble = true;
 456         }
 457     }
 458 
 459     /**
 460      * Writes a string.  This method cannot be inherited from the Writer class
 461      * because it must suppress I/O exceptions.
 462      * @param s String to be written
 463      */
 464     public void write(String s) {
 465         write(s, 0, s.length());
 466     }
 467 
 468     private void newLine() {
 469         try {
 470             synchronized (lock) {
 471                 ensureOpen();
 472                 out.write(System.lineSeparator());
 473                 if (autoFlush)
 474                     out.flush();
 475             }
 476         }
 477         catch (InterruptedIOException x) {
 478             Thread.currentThread().interrupt();
 479         }
 480         catch (IOException x) {
 481             trouble = true;
 482         }
 483     }
 484 
 485     /* Methods that do not terminate lines */
 486 
 487     /**
 488      * Prints a boolean value.  The string produced by <code>{@link
 489      * java.lang.String#valueOf(boolean)}</code> is translated into bytes
 490      * according to the platform's default character encoding, and these bytes
 491      * are written in exactly the manner of the <code>{@link
 492      * #write(int)}</code> method.
 493      *
 494      * @param      b   The <code>boolean</code> to be printed
 495      */
 496     public void print(boolean b) {
 497         write(b ? "true" : "false");
 498     }
 499 
 500     /**
 501      * Prints a character.  The character is translated into one or more bytes
 502      * according to the platform's default character encoding, and these bytes
 503      * are written in exactly the manner of the <code>{@link
 504      * #write(int)}</code> method.
 505      *
 506      * @param      c   The <code>char</code> to be printed
 507      */
 508     public void print(char c) {
 509         write(c);
 510     }
 511 
 512     /**
 513      * Prints an integer.  The string produced by <code>{@link
 514      * java.lang.String#valueOf(int)}</code> is translated into bytes according
 515      * to the platform's default character encoding, and these bytes are
 516      * written in exactly the manner of the <code>{@link #write(int)}</code>
 517      * method.
 518      *
 519      * @param      i   The <code>int</code> to be printed
 520      * @see        java.lang.Integer#toString(int)
 521      */
 522     public void print(int i) {
 523         write(String.valueOf(i));
 524     }
 525 
 526     /**
 527      * Prints a long integer.  The string produced by <code>{@link
 528      * java.lang.String#valueOf(long)}</code> is translated into bytes
 529      * according to the platform's default character encoding, and these bytes
 530      * are written in exactly the manner of the <code>{@link #write(int)}</code>
 531      * method.
 532      *
 533      * @param      l   The <code>long</code> to be printed
 534      * @see        java.lang.Long#toString(long)
 535      */
 536     public void print(long l) {
 537         write(String.valueOf(l));
 538     }
 539 
 540     /**
 541      * Prints a floating-point number.  The string produced by <code>{@link
 542      * java.lang.String#valueOf(float)}</code> is translated into bytes
 543      * according to the platform's default character encoding, and these bytes
 544      * are written in exactly the manner of the <code>{@link #write(int)}</code>
 545      * method.
 546      *
 547      * @param      f   The <code>float</code> to be printed
 548      * @see        java.lang.Float#toString(float)
 549      */
 550     public void print(float f) {
 551         write(String.valueOf(f));
 552     }
 553 
 554     /**
 555      * Prints a double-precision floating-point number.  The string produced by
 556      * <code>{@link java.lang.String#valueOf(double)}</code> is translated into
 557      * bytes according to the platform's default character encoding, and these
 558      * bytes are written in exactly the manner of the <code>{@link
 559      * #write(int)}</code> method.
 560      *
 561      * @param      d   The <code>double</code> to be printed
 562      * @see        java.lang.Double#toString(double)
 563      */
 564     public void print(double d) {
 565         write(String.valueOf(d));
 566     }
 567 
 568     /**
 569      * Prints an array of characters.  The characters are converted into bytes
 570      * according to the platform's default character encoding, and these bytes
 571      * are written in exactly the manner of the <code>{@link #write(int)}</code>
 572      * method.
 573      *
 574      * @param      s   The array of chars to be printed
 575      *
 576      * @throws  NullPointerException  If <code>s</code> is <code>null</code>
 577      */
 578     public void print(char s[]) {
 579         write(s);
 580     }
 581 
 582     /**
 583      * Prints a string.  If the argument is <code>null</code> then the string
 584      * <code>"null"</code> is printed.  Otherwise, the string's characters are
 585      * converted into bytes according to the platform's default character
 586      * encoding, and these bytes are written in exactly the manner of the
 587      * <code>{@link #write(int)}</code> method.
 588      *
 589      * @param      s   The <code>String</code> to be printed
 590      */
 591     public void print(String s) {
 592         if (s == null) {
 593             s = "null";
 594         }
 595         write(s);
 596     }
 597 
 598     /**
 599      * Prints an object.  The string produced by the <code>{@link
 600      * java.lang.String#valueOf(Object)}</code> method is translated into bytes
 601      * according to the platform's default character encoding, and these bytes
 602      * are written in exactly the manner of the <code>{@link #write(int)}</code>
 603      * method.
 604      *
 605      * @param      obj   The <code>Object</code> to be printed
 606      * @see        java.lang.Object#toString()
 607      */
 608     public void print(Object obj) {
 609         write(String.valueOf(obj));
 610     }
 611 
 612     /* Methods that do terminate lines */
 613 
 614     /**
 615      * Terminates the current line by writing the line separator string.  The
 616      * line separator string is defined by the system property
 617      * <code>line.separator</code>, and is not necessarily a single newline
 618      * character (<code>'\n'</code>).
 619      */
 620     public void println() {
 621         newLine();
 622     }
 623 
 624     /**
 625      * Prints a boolean value and then terminates the line.  This method behaves
 626      * as though it invokes <code>{@link #print(boolean)}</code> and then
 627      * <code>{@link #println()}</code>.
 628      *
 629      * @param x the <code>boolean</code> value to be printed
 630      */
 631     public void println(boolean x) {
 632         synchronized (lock) {
 633             print(x);
 634             println();
 635         }
 636     }
 637 
 638     /**
 639      * Prints a character and then terminates the line.  This method behaves as
 640      * though it invokes <code>{@link #print(char)}</code> and then <code>{@link
 641      * #println()}</code>.
 642      *
 643      * @param x the <code>char</code> value to be printed
 644      */
 645     public void println(char x) {
 646         synchronized (lock) {
 647             print(x);
 648             println();
 649         }
 650     }
 651 
 652     /**
 653      * Prints an integer and then terminates the line.  This method behaves as
 654      * though it invokes <code>{@link #print(int)}</code> and then <code>{@link
 655      * #println()}</code>.
 656      *
 657      * @param x the <code>int</code> value to be printed
 658      */
 659     public void println(int x) {
 660         synchronized (lock) {
 661             print(x);
 662             println();
 663         }
 664     }
 665 
 666     /**
 667      * Prints a long integer and then terminates the line.  This method behaves
 668      * as though it invokes <code>{@link #print(long)}</code> and then
 669      * <code>{@link #println()}</code>.
 670      *
 671      * @param x the <code>long</code> value to be printed
 672      */
 673     public void println(long x) {
 674         synchronized (lock) {
 675             print(x);
 676             println();
 677         }
 678     }
 679 
 680     /**
 681      * Prints a floating-point number and then terminates the line.  This method
 682      * behaves as though it invokes <code>{@link #print(float)}</code> and then
 683      * <code>{@link #println()}</code>.
 684      *
 685      * @param x the <code>float</code> value to be printed
 686      */
 687     public void println(float x) {
 688         synchronized (lock) {
 689             print(x);
 690             println();
 691         }
 692     }
 693 
 694     /**
 695      * Prints a double-precision floating-point number and then terminates the
 696      * line.  This method behaves as though it invokes <code>{@link
 697      * #print(double)}</code> and then <code>{@link #println()}</code>.
 698      *
 699      * @param x the <code>double</code> value to be printed
 700      */
 701     public void println(double x) {
 702         synchronized (lock) {
 703             print(x);
 704             println();
 705         }
 706     }
 707 
 708     /**
 709      * Prints an array of characters and then terminates the line.  This method
 710      * behaves as though it invokes <code>{@link #print(char[])}</code> and then
 711      * <code>{@link #println()}</code>.
 712      *
 713      * @param x the array of <code>char</code> values to be printed
 714      */
 715     public void println(char x[]) {
 716         synchronized (lock) {
 717             print(x);
 718             println();
 719         }
 720     }
 721 
 722     /**
 723      * Prints a String and then terminates the line.  This method behaves as
 724      * though it invokes <code>{@link #print(String)}</code> and then
 725      * <code>{@link #println()}</code>.
 726      *
 727      * @param x the <code>String</code> value to be printed
 728      */
 729     public void println(String x) {
 730         synchronized (lock) {
 731             print(x);
 732             println();
 733         }
 734     }
 735 
 736     /**
 737      * Prints an Object and then terminates the line.  This method calls
 738      * at first String.valueOf(x) to get the printed object's string value,
 739      * then behaves as
 740      * though it invokes <code>{@link #print(String)}</code> and then
 741      * <code>{@link #println()}</code>.
 742      *
 743      * @param x  The <code>Object</code> to be printed.
 744      */
 745     public void println(Object x) {
 746         String s = String.valueOf(x);
 747         synchronized (lock) {
 748             print(s);
 749             println();
 750         }
 751     }
 752 
 753     /**
 754      * A convenience method to write a formatted string to this writer using
 755      * the specified format string and arguments.  If automatic flushing is
 756      * enabled, calls to this method will flush the output buffer.
 757      *
 758      * <p> An invocation of this method of the form <tt>out.printf(format,
 759      * args)</tt> behaves in exactly the same way as the invocation
 760      *
 761      * <pre>
 762      *     out.format(format, args) </pre>
 763      *
 764      * @param  format
 765      *         A format string as described in <a
 766      *         href="../util/Formatter.html#syntax">Format string syntax</a>.
 767      *
 768      * @param  args
 769      *         Arguments referenced by the format specifiers in the format
 770      *         string.  If there are more arguments than format specifiers, the
 771      *         extra arguments are ignored.  The number of arguments is
 772      *         variable and may be zero.  The maximum number of arguments is
 773      *         limited by the maximum dimension of a Java array as defined by
 774      *         <cite>The Java&trade; Virtual Machine Specification</cite>.
 775      *         The behaviour on a
 776      *         <tt>null</tt> argument depends on the <a
 777      *         href="../util/Formatter.html#syntax">conversion</a>.
 778      *
 779      * @throws  java.util.IllegalFormatException
 780      *          If a format string contains an illegal syntax, a format
 781      *          specifier that is incompatible with the given arguments,
 782      *          insufficient arguments given the format string, or other
 783      *          illegal conditions.  For specification of all possible
 784      *          formatting errors, see the <a
 785      *          href="../util/Formatter.html#detail">Details</a> section of the
 786      *          formatter class specification.
 787      *
 788      * @throws  NullPointerException
 789      *          If the <tt>format</tt> is <tt>null</tt>
 790      *
 791      * @return  This writer
 792      *
 793      * @since  1.5
 794      */
 795     public PrintWriter printf(String format, Object ... args) {
 796         return format(format, args);
 797     }
 798 
 799     /**
 800      * A convenience method to write a formatted string to this writer using
 801      * the specified format string and arguments.  If automatic flushing is
 802      * enabled, calls to this method will flush the output buffer.
 803      *
 804      * <p> An invocation of this method of the form <tt>out.printf(l, format,
 805      * args)</tt> behaves in exactly the same way as the invocation
 806      *
 807      * <pre>
 808      *     out.format(l, format, args) </pre>
 809      *
 810      * @param  l
 811      *         The {@linkplain java.util.Locale locale} to apply during
 812      *         formatting.  If <tt>l</tt> is <tt>null</tt> then no localization
 813      *         is applied.
 814      *
 815      * @param  format
 816      *         A format string as described in <a
 817      *         href="../util/Formatter.html#syntax">Format string syntax</a>.
 818      *
 819      * @param  args
 820      *         Arguments referenced by the format specifiers in the format
 821      *         string.  If there are more arguments than format specifiers, the
 822      *         extra arguments are ignored.  The number of arguments is
 823      *         variable and may be zero.  The maximum number of arguments is
 824      *         limited by the maximum dimension of a Java array as defined by
 825      *         <cite>The Java&trade; Virtual Machine Specification</cite>.
 826      *         The behaviour on a
 827      *         <tt>null</tt> argument depends on the <a
 828      *         href="../util/Formatter.html#syntax">conversion</a>.
 829      *
 830      * @throws  java.util.IllegalFormatException
 831      *          If a format string contains an illegal syntax, a format
 832      *          specifier that is incompatible with the given arguments,
 833      *          insufficient arguments given the format string, or other
 834      *          illegal conditions.  For specification of all possible
 835      *          formatting errors, see the <a
 836      *          href="../util/Formatter.html#detail">Details</a> section of the
 837      *          formatter class specification.
 838      *
 839      * @throws  NullPointerException
 840      *          If the <tt>format</tt> is <tt>null</tt>
 841      *
 842      * @return  This writer
 843      *
 844      * @since  1.5
 845      */
 846     public PrintWriter printf(Locale l, String format, Object ... args) {
 847         return format(l, format, args);
 848     }
 849 
 850     /**
 851      * Writes a formatted string to this writer using the specified format
 852      * string and arguments.  If automatic flushing is enabled, calls to this
 853      * method will flush the output buffer.
 854      *
 855      * <p> The locale always used is the one returned by {@link
 856      * java.util.Locale#getDefault() Locale.getDefault()}, regardless of any
 857      * previous invocations of other formatting methods on this object.
 858      *
 859      * @param  format
 860      *         A format string as described in <a
 861      *         href="../util/Formatter.html#syntax">Format string syntax</a>.
 862      *
 863      * @param  args
 864      *         Arguments referenced by the format specifiers in the format
 865      *         string.  If there are more arguments than format specifiers, the
 866      *         extra arguments are ignored.  The number of arguments is
 867      *         variable and may be zero.  The maximum number of arguments is
 868      *         limited by the maximum dimension of a Java array as defined by
 869      *         <cite>The Java&trade; Virtual Machine Specification</cite>.
 870      *         The behaviour on a
 871      *         <tt>null</tt> argument depends on the <a
 872      *         href="../util/Formatter.html#syntax">conversion</a>.
 873      *
 874      * @throws  java.util.IllegalFormatException
 875      *          If a format string contains an illegal syntax, a format
 876      *          specifier that is incompatible with the given arguments,
 877      *          insufficient arguments given the format string, or other
 878      *          illegal conditions.  For specification of all possible
 879      *          formatting errors, see the <a
 880      *          href="../util/Formatter.html#detail">Details</a> section of the
 881      *          Formatter class specification.
 882      *
 883      * @throws  NullPointerException
 884      *          If the <tt>format</tt> is <tt>null</tt>
 885      *
 886      * @return  This writer
 887      *
 888      * @since  1.5
 889      */
 890     public PrintWriter format(String format, Object ... args) {
 891         try {
 892             synchronized (lock) {
 893                 ensureOpen();
 894                 if ((formatter == null)
 895                     || (formatter.locale() != Locale.getDefault()))
 896                     formatter = new Formatter(this);
 897                 formatter.format(Locale.getDefault(), format, args);
 898                 if (autoFlush)
 899                     out.flush();
 900             }
 901         } catch (InterruptedIOException x) {
 902             Thread.currentThread().interrupt();
 903         } catch (IOException x) {
 904             trouble = true;
 905         }
 906         return this;
 907     }
 908 
 909     /**
 910      * Writes a formatted string to this writer using the specified format
 911      * string and arguments.  If automatic flushing is enabled, calls to this
 912      * method will flush the output buffer.
 913      *
 914      * @param  l
 915      *         The {@linkplain java.util.Locale locale} to apply during
 916      *         formatting.  If <tt>l</tt> is <tt>null</tt> then no localization
 917      *         is applied.
 918      *
 919      * @param  format
 920      *         A format string as described in <a
 921      *         href="../util/Formatter.html#syntax">Format string syntax</a>.
 922      *
 923      * @param  args
 924      *         Arguments referenced by the format specifiers in the format
 925      *         string.  If there are more arguments than format specifiers, the
 926      *         extra arguments are ignored.  The number of arguments is
 927      *         variable and may be zero.  The maximum number of arguments is
 928      *         limited by the maximum dimension of a Java array as defined by
 929      *         <cite>The Java&trade; Virtual Machine Specification</cite>.
 930      *         The behaviour on a
 931      *         <tt>null</tt> argument depends on the <a
 932      *         href="../util/Formatter.html#syntax">conversion</a>.
 933      *
 934      * @throws  java.util.IllegalFormatException
 935      *          If a format string contains an illegal syntax, a format
 936      *          specifier that is incompatible with the given arguments,
 937      *          insufficient arguments given the format string, or other
 938      *          illegal conditions.  For specification of all possible
 939      *          formatting errors, see the <a
 940      *          href="../util/Formatter.html#detail">Details</a> section of the
 941      *          formatter class specification.
 942      *
 943      * @throws  NullPointerException
 944      *          If the <tt>format</tt> is <tt>null</tt>
 945      *
 946      * @return  This writer
 947      *
 948      * @since  1.5
 949      */
 950     public PrintWriter format(Locale l, String format, Object ... args) {
 951         try {
 952             synchronized (lock) {
 953                 ensureOpen();
 954                 if ((formatter == null) || (formatter.locale() != l))
 955                     formatter = new Formatter(this, l);
 956                 formatter.format(l, format, args);
 957                 if (autoFlush)
 958                     out.flush();
 959             }
 960         } catch (InterruptedIOException x) {
 961             Thread.currentThread().interrupt();
 962         } catch (IOException x) {
 963             trouble = true;
 964         }
 965         return this;
 966     }
 967 
 968     /**
 969      * Appends the specified character sequence to this writer.
 970      *
 971      * <p> An invocation of this method of the form <tt>out.append(csq)</tt>
 972      * behaves in exactly the same way as the invocation
 973      *
 974      * <pre>
 975      *     out.write(csq.toString()) </pre>
 976      *
 977      * <p> Depending on the specification of <tt>toString</tt> for the
 978      * character sequence <tt>csq</tt>, the entire sequence may not be
 979      * appended. For instance, invoking the <tt>toString</tt> method of a
 980      * character buffer will return a subsequence whose content depends upon
 981      * the buffer's position and limit.
 982      *
 983      * @param  csq
 984      *         The character sequence to append.  If <tt>csq</tt> is
 985      *         <tt>null</tt>, then the four characters <tt>"null"</tt> are
 986      *         appended to this writer.
 987      *
 988      * @return  This writer
 989      *
 990      * @since  1.5
 991      */
 992     public PrintWriter append(CharSequence csq) {
 993         if (csq == null)
 994             write("null");
 995         else
 996             write(csq.toString());
 997         return this;
 998     }
 999 
1000     /**
1001      * Appends a subsequence of the specified character sequence to this writer.
1002      *
1003      * <p> An invocation of this method of the form <tt>out.append(csq, start,
1004      * end)</tt> when <tt>csq</tt> is not <tt>null</tt>, behaves in
1005      * exactly the same way as the invocation
1006      *
1007      * <pre>
1008      *     out.write(csq.subSequence(start, end).toString()) </pre>
1009      *
1010      * @param  csq
1011      *         The character sequence from which a subsequence will be
1012      *         appended.  If <tt>csq</tt> is <tt>null</tt>, then characters
1013      *         will be appended as if <tt>csq</tt> contained the four
1014      *         characters <tt>"null"</tt>.
1015      *
1016      * @param  start
1017      *         The index of the first character in the subsequence
1018      *
1019      * @param  end
1020      *         The index of the character following the last character in the
1021      *         subsequence
1022      *
1023      * @return  This writer
1024      *
1025      * @throws  IndexOutOfBoundsException
1026      *          If <tt>start</tt> or <tt>end</tt> are negative, <tt>start</tt>
1027      *          is greater than <tt>end</tt>, or <tt>end</tt> is greater than
1028      *          <tt>csq.length()</tt>
1029      *
1030      * @since  1.5
1031      */
1032     public PrintWriter append(CharSequence csq, int start, int end) {
1033         CharSequence cs = (csq == null ? "null" : csq);
1034         write(cs.subSequence(start, end).toString());
1035         return this;
1036     }
1037 
1038     /**
1039      * Appends the specified character to this writer.
1040      *
1041      * <p> An invocation of this method of the form <tt>out.append(c)</tt>
1042      * behaves in exactly the same way as the invocation
1043      *
1044      * <pre>
1045      *     out.write(c) </pre>
1046      *
1047      * @param  c
1048      *         The 16-bit character to append
1049      *
1050      * @return  This writer
1051      *
1052      * @since 1.5
1053      */
1054     public PrintWriter append(char c) {
1055         write(c);
1056         return this;
1057     }
1058 }