1 /* 2 * Copyright (C) 2014 The Android Open Source Project 3 * Copyright (c) 1996, 2017, Oracle and/or its affiliates. All rights reserved. 4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 5 * 6 * This code is free software; you can redistribute it and/or modify it 7 * under the terms of the GNU General Public License version 2 only, as 8 * published by the Free Software Foundation. Oracle designates this 9 * particular file as subject to the "Classpath" exception as provided 10 * by Oracle in the LICENSE file that accompanied this code. 11 * 12 * This code is distributed in the hope that it will be useful, but WITHOUT 13 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 14 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15 * version 2 for more details (a copy is included in the LICENSE file that 16 * accompanied this code). 17 * 18 * You should have received a copy of the GNU General Public License version 19 * 2 along with this work; if not, write to the Free Software Foundation, 20 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 21 * 22 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 23 * or visit www.oracle.com if you need additional information or have any 24 * questions. 25 */ 26 27 package java.io; 28 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 * A {@code PrintStream} adds functionality to another output stream, 37 * namely the ability to print representations of various data values 38 * conveniently. Two other features are provided as well. Unlike other output 39 * streams, a {@code PrintStream} never throws an 40 * {@code IOException}; instead, exceptional situations merely set an 41 * internal flag that can be tested via the {@code checkError} method. 42 * Optionally, a {@code PrintStream} can be created so as to flush 43 * automatically; this means that the {@code flush} method is 44 * automatically invoked after a byte array is written, one of the 45 * {@code println} methods is invoked, or a newline character or byte 46 * ({@code '\n'}) is written. 47 * 48 * <p> All characters printed by a {@code PrintStream} are converted into 49 * bytes using the given encoding or charset, or platform's default character 50 * encoding if not specified. 51 * The {@link PrintWriter} class should be used in situations that require 52 * writing characters rather than bytes. 53 * 54 * <p> This class always replaces malformed and unmappable character sequences with 55 * the charset's default replacement string. 56 * The {@linkplain java.nio.charset.CharsetEncoder} class should be used when more 57 * control over the encoding process is required. 58 * 59 * @author Frank Yellin 60 * @author Mark Reinhold 61 * @since 1.0 62 */ 63 64 public class PrintStream extends FilterOutputStream 65 implements Appendable, Closeable 66 { 67 68 private final boolean autoFlush; 69 private boolean trouble = false; 70 private Formatter formatter; 71 72 /** 73 * Track both the text- and character-output streams, so that their buffers 74 * can be flushed without flushing the entire stream. 75 */ 76 private BufferedWriter textOut; 77 private OutputStreamWriter charOut; 78 79 // Android-added: Lazy initialization of charOut and textOut. 80 private Charset charset; 81 82 /** 83 * requireNonNull is explicitly declared here so as not to create an extra 84 * dependency on java.util.Objects.requireNonNull. PrintStream is loaded 85 * early during system initialization. 86 */ requireNonNull(T obj, String message)87 private static <T> T requireNonNull(T obj, String message) { 88 if (obj == null) 89 throw new NullPointerException(message); 90 return obj; 91 } 92 93 /** 94 * Returns a charset object for the given charset name. 95 * @throws NullPointerException is csn is null 96 * @throws UnsupportedEncodingException if the charset is not supported 97 */ toCharset(String csn)98 private static Charset toCharset(String csn) 99 throws UnsupportedEncodingException 100 { 101 requireNonNull(csn, "charsetName"); 102 try { 103 return Charset.forName(csn); 104 } catch (IllegalCharsetNameException|UnsupportedCharsetException unused) { 105 // UnsupportedEncodingException should be thrown 106 throw new UnsupportedEncodingException(csn); 107 } 108 } 109 110 /* Private constructors */ PrintStream(boolean autoFlush, OutputStream out)111 private PrintStream(boolean autoFlush, OutputStream out) { 112 super(out); 113 this.autoFlush = autoFlush; 114 // Android-changed: Lazy initialization of charOut and textOut. 115 // this.charOut = new OutputStreamWriter(this); 116 // this.textOut = new BufferedWriter(charOut); 117 } 118 119 /* Variant of the private constructor so that the given charset name 120 * can be verified before evaluating the OutputStream argument. Used 121 * by constructors creating a FileOutputStream that also take a 122 * charset name. 123 */ PrintStream(boolean autoFlush, Charset charset, OutputStream out)124 private PrintStream(boolean autoFlush, Charset charset, OutputStream out) { 125 this(out, autoFlush, charset); 126 } 127 128 /** 129 * Creates a new print stream. This stream will not flush automatically. 130 * 131 * @param out The output stream to which values and objects will be 132 * printed 133 * 134 * @see java.io.PrintWriter#PrintWriter(java.io.OutputStream) 135 */ PrintStream(OutputStream out)136 public PrintStream(OutputStream out) { 137 this(out, false); 138 } 139 140 /** 141 * Creates a new print stream. 142 * 143 * @param out The output stream to which values and objects will be 144 * printed 145 * @param autoFlush A boolean; if true, the output buffer will be flushed 146 * whenever a byte array is written, one of the 147 * {@code println} methods is invoked, or a newline 148 * character or byte ({@code '\n'}) is written 149 * 150 * @see java.io.PrintWriter#PrintWriter(java.io.OutputStream, boolean) 151 */ PrintStream(OutputStream out, boolean autoFlush)152 public PrintStream(OutputStream out, boolean autoFlush) { 153 this(autoFlush, requireNonNull(out, "Null output stream")); 154 } 155 156 /** 157 * Creates a new print stream. 158 * 159 * @param out The output stream to which values and objects will be 160 * printed 161 * @param autoFlush A boolean; if true, the output buffer will be flushed 162 * whenever a byte array is written, one of the 163 * {@code println} methods is invoked, or a newline 164 * character or byte ({@code '\n'}) is written 165 * @param encoding The name of a supported 166 * <a href="../lang/package-summary.html#charenc"> 167 * character encoding</a> 168 * 169 * @throws UnsupportedEncodingException 170 * If the named encoding is not supported 171 * 172 * @since 1.4 173 */ PrintStream(OutputStream out, boolean autoFlush, String encoding)174 public PrintStream(OutputStream out, boolean autoFlush, String encoding) 175 throws UnsupportedEncodingException 176 { 177 this(requireNonNull(out, "Null output stream"), autoFlush, toCharset(encoding)); 178 } 179 180 /** 181 * Creates a new print stream, with the specified OutputStream, automatic line 182 * flushing and charset. This convenience constructor creates the necessary 183 * intermediate {@link java.io.OutputStreamWriter OutputStreamWriter}, 184 * which will encode characters using the provided charset. 185 * 186 * @param out The output stream to which values and objects will be 187 * printed 188 * @param autoFlush A boolean; if true, the output buffer will be flushed 189 * whenever a byte array is written, one of the 190 * {@code println} methods is invoked, or a newline 191 * character or byte ({@code '\n'}) is written 192 * @param charset A {@linkplain java.nio.charset.Charset charset} 193 * 194 * @since 10 195 */ PrintStream(OutputStream out, boolean autoFlush, Charset charset)196 public PrintStream(OutputStream out, boolean autoFlush, Charset charset) { 197 super(out); 198 this.autoFlush = autoFlush; 199 this.charOut = new OutputStreamWriter(this, charset); 200 this.textOut = new BufferedWriter(charOut); 201 } 202 203 /** 204 * Creates a new print stream, without automatic line flushing, with the 205 * specified file name. This convenience constructor creates 206 * the necessary intermediate {@link java.io.OutputStreamWriter 207 * OutputStreamWriter}, which will encode characters using the 208 * {@linkplain java.nio.charset.Charset#defaultCharset() default charset} 209 * for this instance of the Java virtual machine. 210 * 211 * @param fileName 212 * The name of the file to use as the destination of this print 213 * stream. If the file exists, then it will be truncated to 214 * zero size; otherwise, a new file will be created. The output 215 * will be written to the file and is buffered. 216 * 217 * @throws FileNotFoundException 218 * If the given file object does not denote an existing, writable 219 * regular file and a new regular file of that name cannot be 220 * created, or if some other error occurs while opening or 221 * creating the file 222 * 223 * @throws SecurityException 224 * If a security manager is present and {@link 225 * SecurityManager#checkWrite checkWrite(fileName)} denies write 226 * access to the file 227 * 228 * @since 1.5 229 */ PrintStream(String fileName)230 public PrintStream(String fileName) throws FileNotFoundException { 231 this(false, new FileOutputStream(fileName)); 232 } 233 234 /** 235 * Creates a new print stream, without automatic line flushing, with the 236 * specified file name and charset. This convenience constructor creates 237 * the necessary intermediate {@link java.io.OutputStreamWriter 238 * OutputStreamWriter}, which will encode characters using the provided 239 * charset. 240 * 241 * @param fileName 242 * The name of the file to use as the destination of this print 243 * stream. If the file exists, then it will be truncated to 244 * zero size; otherwise, a new file will be created. The output 245 * will be written to the file and is buffered. 246 * 247 * @param csn 248 * The name of a supported {@linkplain java.nio.charset.Charset 249 * charset} 250 * 251 * @throws FileNotFoundException 252 * If the given file object does not denote an existing, writable 253 * regular file and a new regular file of that name cannot be 254 * created, or if some other error occurs while opening or 255 * creating the file 256 * 257 * @throws SecurityException 258 * If a security manager is present and {@link 259 * SecurityManager#checkWrite checkWrite(fileName)} denies write 260 * access to the file 261 * 262 * @throws UnsupportedEncodingException 263 * If the named charset is not supported 264 * 265 * @since 1.5 266 */ PrintStream(String fileName, String csn)267 public PrintStream(String fileName, String csn) 268 throws FileNotFoundException, UnsupportedEncodingException 269 { 270 // ensure charset is checked before the file is opened 271 this(false, toCharset(csn), new FileOutputStream(fileName)); 272 } 273 274 /** 275 * Creates a new print stream, without automatic line flushing, with the 276 * specified file name and charset. This convenience constructor creates 277 * the necessary intermediate {@link java.io.OutputStreamWriter 278 * OutputStreamWriter}, which will encode characters using the provided 279 * charset. 280 * 281 * @param fileName 282 * The name of the file to use as the destination of this print 283 * stream. If the file exists, then it will be truncated to 284 * zero size; otherwise, a new file will be created. The output 285 * will be written to the file and is buffered. 286 * 287 * @param charset 288 * A {@linkplain java.nio.charset.Charset charset} 289 * 290 * @throws IOException 291 * if an I/O error occurs while opening or creating the file 292 * 293 * @throws SecurityException 294 * If a security manager is present and {@link 295 * SecurityManager#checkWrite checkWrite(fileName)} denies write 296 * access to the file 297 * 298 * @since 10 299 */ PrintStream(String fileName, Charset charset)300 public PrintStream(String fileName, Charset charset) throws IOException { 301 this(false, requireNonNull(charset, "charset"), new FileOutputStream(fileName)); 302 } 303 304 /** 305 * Creates a new print stream, without automatic line flushing, with the 306 * specified file. This convenience constructor creates the necessary 307 * intermediate {@link java.io.OutputStreamWriter OutputStreamWriter}, 308 * which will encode characters using the {@linkplain 309 * java.nio.charset.Charset#defaultCharset() default charset} for this 310 * instance of the Java virtual machine. 311 * 312 * @param file 313 * The file to use as the destination of this print stream. If the 314 * file exists, then it will be truncated to zero size; otherwise, 315 * a new file will be created. The output will be written to the 316 * file and is buffered. 317 * 318 * @throws FileNotFoundException 319 * If the given file object does not denote an existing, writable 320 * regular file and a new regular file of that name cannot be 321 * created, or if some other error occurs while opening or 322 * creating the file 323 * 324 * @throws SecurityException 325 * If a security manager is present and {@link 326 * SecurityManager#checkWrite checkWrite(file.getPath())} 327 * denies write access to the file 328 * 329 * @since 1.5 330 */ PrintStream(File file)331 public PrintStream(File file) throws FileNotFoundException { 332 this(false, new FileOutputStream(file)); 333 } 334 335 /** 336 * Creates a new print stream, without automatic line flushing, with the 337 * specified file and charset. This convenience constructor creates 338 * the necessary intermediate {@link java.io.OutputStreamWriter 339 * OutputStreamWriter}, which will encode characters using the provided 340 * charset. 341 * 342 * @param file 343 * The file to use as the destination of this print stream. If the 344 * file exists, then it will be truncated to zero size; otherwise, 345 * a new file will be created. The output will be written to the 346 * file and is buffered. 347 * 348 * @param csn 349 * The name of a supported {@linkplain java.nio.charset.Charset 350 * charset} 351 * 352 * @throws FileNotFoundException 353 * If the given file object does not denote an existing, writable 354 * regular file and a new regular file of that name cannot be 355 * created, or if some other error occurs while opening or 356 * creating the file 357 * 358 * @throws SecurityException 359 * If a security manager is present and {@link 360 * SecurityManager#checkWrite checkWrite(file.getPath())} 361 * denies write access to the file 362 * 363 * @throws UnsupportedEncodingException 364 * If the named charset is not supported 365 * 366 * @since 1.5 367 */ PrintStream(File file, String csn)368 public PrintStream(File file, String csn) 369 throws FileNotFoundException, UnsupportedEncodingException 370 { 371 // ensure charset is checked before the file is opened 372 this(false, toCharset(csn), new FileOutputStream(file)); 373 } 374 375 376 /** 377 * Creates a new print stream, without automatic line flushing, with the 378 * specified file and charset. This convenience constructor creates 379 * the necessary intermediate {@link java.io.OutputStreamWriter 380 * OutputStreamWriter}, which will encode characters using the provided 381 * charset. 382 * 383 * @param file 384 * The file to use as the destination of this print stream. If the 385 * file exists, then it will be truncated to zero size; otherwise, 386 * a new file will be created. The output will be written to the 387 * file and is buffered. 388 * 389 * @param charset 390 * A {@linkplain java.nio.charset.Charset charset} 391 * 392 * @throws IOException 393 * if an I/O error occurs while opening or creating the file 394 * 395 * @throws SecurityException 396 * If a security manager is present and {@link 397 * SecurityManager#checkWrite checkWrite(file.getPath())} 398 * denies write access to the file 399 * 400 * @since 10 401 */ PrintStream(File file, Charset charset)402 public PrintStream(File file, Charset charset) throws IOException { 403 this(false, requireNonNull(charset, "charset"), new FileOutputStream(file)); 404 } 405 406 /** Check to make sure that the stream has not been closed */ ensureOpen()407 private void ensureOpen() throws IOException { 408 if (out == null) 409 throw new IOException("Stream closed"); 410 } 411 412 /** 413 * Flushes the stream. This is done by writing any buffered output bytes to 414 * the underlying output stream and then flushing that stream. 415 * 416 * @see java.io.OutputStream#flush() 417 */ flush()418 public void flush() { 419 synchronized (this) { 420 try { 421 ensureOpen(); 422 out.flush(); 423 } 424 catch (IOException x) { 425 trouble = true; 426 } 427 } 428 } 429 430 private boolean closing = false; /* To avoid recursive closing */ 431 432 // BEGIN Android-added: Lazy initialization of charOut and textOut. getTextOut()433 private BufferedWriter getTextOut() { 434 if (textOut == null) { 435 charOut = charset != null ? new OutputStreamWriter(this, charset) : 436 new OutputStreamWriter(this); 437 textOut = new BufferedWriter(charOut); 438 } 439 return textOut; 440 } 441 // END Android-added: Lazy initialization of charOut and textOut. 442 443 /** 444 * Closes the stream. This is done by flushing the stream and then closing 445 * the underlying output stream. 446 * 447 * @see java.io.OutputStream#close() 448 */ close()449 public void close() { 450 synchronized (this) { 451 if (! closing) { 452 closing = true; 453 try { 454 // BEGIN Android-changed: Lazy initialization of charOut and textOut. 455 // textOut.close(); 456 if (textOut != null) { 457 textOut.close(); 458 } 459 // END Android-changed: Lazy initialization of charOut and textOut. 460 out.close(); 461 } 462 catch (IOException x) { 463 trouble = true; 464 } 465 textOut = null; 466 charOut = null; 467 out = null; 468 } 469 } 470 } 471 472 /** 473 * Flushes the stream and checks its error state. The internal error state 474 * is set to {@code true} when the underlying output stream throws an 475 * {@code IOException} other than {@code InterruptedIOException}, 476 * and when the {@code setError} method is invoked. If an operation 477 * on the underlying output stream throws an 478 * {@code InterruptedIOException}, then the {@code PrintStream} 479 * converts the exception back into an interrupt by doing: 480 * <pre>{@code 481 * Thread.currentThread().interrupt(); 482 * }</pre> 483 * or the equivalent. 484 * 485 * @return {@code true} if and only if this stream has encountered an 486 * {@code IOException} other than 487 * {@code InterruptedIOException}, or the 488 * {@code setError} method has been invoked 489 */ checkError()490 public boolean checkError() { 491 if (out != null) 492 flush(); 493 if (out instanceof java.io.PrintStream) { 494 PrintStream ps = (PrintStream) out; 495 return ps.checkError(); 496 } 497 return trouble; 498 } 499 500 /** 501 * Sets the error state of the stream to {@code true}. 502 * 503 * <p> This method will cause subsequent invocations of {@link 504 * #checkError()} to return {@code true} until 505 * {@link #clearError()} is invoked. 506 * 507 * @since 1.1 508 */ setError()509 protected void setError() { 510 trouble = true; 511 } 512 513 /** 514 * Clears the internal error state of this stream. 515 * 516 * <p> This method will cause subsequent invocations of {@link 517 * #checkError()} to return {@code false} until another write 518 * operation fails and invokes {@link #setError()}. 519 * 520 * @since 1.6 521 */ clearError()522 protected void clearError() { 523 trouble = false; 524 } 525 526 /* 527 * Exception-catching, synchronized output operations, 528 * which also implement the write() methods of OutputStream 529 */ 530 531 /** 532 * Writes the specified byte to this stream. If the byte is a newline and 533 * automatic flushing is enabled then the {@code flush} method will be 534 * invoked. 535 * 536 * <p> Note that the byte is written as given; to write a character that 537 * will be translated according to the platform's default character 538 * encoding, use the {@code print(char)} or {@code println(char)} 539 * methods. 540 * 541 * @param b The byte to be written 542 * @see #print(char) 543 * @see #println(char) 544 */ write(int b)545 public void write(int b) { 546 try { 547 synchronized (this) { 548 ensureOpen(); 549 out.write(b); 550 if ((b == '\n') && autoFlush) 551 out.flush(); 552 } 553 } 554 catch (InterruptedIOException x) { 555 Thread.currentThread().interrupt(); 556 } 557 catch (IOException x) { 558 trouble = true; 559 } 560 } 561 562 /** 563 * Writes {@code len} bytes from the specified byte array starting at 564 * offset {@code off} to this stream. If automatic flushing is 565 * enabled then the {@code flush} method will be invoked. 566 * 567 * <p> Note that the bytes will be written as given; to write characters 568 * that will be translated according to the platform's default character 569 * encoding, use the {@code print(char)} or {@code println(char)} 570 * methods. 571 * 572 * @param buf A byte array 573 * @param off Offset from which to start taking bytes 574 * @param len Number of bytes to write 575 */ write(byte buf[], int off, int len)576 public void write(byte buf[], int off, int len) { 577 try { 578 synchronized (this) { 579 ensureOpen(); 580 out.write(buf, off, len); 581 if (autoFlush) 582 out.flush(); 583 } 584 } 585 catch (InterruptedIOException x) { 586 Thread.currentThread().interrupt(); 587 } 588 catch (IOException x) { 589 trouble = true; 590 } 591 } 592 593 /* 594 * The following private methods on the text- and character-output streams 595 * always flush the stream buffers, so that writes to the underlying byte 596 * stream occur as promptly as with the original PrintStream. 597 */ 598 write(char buf[])599 private void write(char buf[]) { 600 try { 601 synchronized (this) { 602 ensureOpen(); 603 // Android-added: Lazy initialization of charOut and textOut. 604 BufferedWriter textOut = getTextOut(); 605 textOut.write(buf); 606 textOut.flushBuffer(); 607 charOut.flushBuffer(); 608 if (autoFlush) { 609 for (int i = 0; i < buf.length; i++) 610 if (buf[i] == '\n') 611 out.flush(); 612 } 613 } 614 } 615 catch (InterruptedIOException x) { 616 Thread.currentThread().interrupt(); 617 } 618 catch (IOException x) { 619 trouble = true; 620 } 621 } 622 write(String s)623 private void write(String s) { 624 try { 625 synchronized (this) { 626 ensureOpen(); 627 // Android-added: Lazy initialization of charOut and textOut. 628 BufferedWriter textOut = getTextOut(); 629 textOut.write(s); 630 textOut.flushBuffer(); 631 charOut.flushBuffer(); 632 if (autoFlush && (s.indexOf('\n') >= 0)) 633 out.flush(); 634 } 635 } 636 catch (InterruptedIOException x) { 637 Thread.currentThread().interrupt(); 638 } 639 catch (IOException x) { 640 trouble = true; 641 } 642 } 643 newLine()644 private void newLine() { 645 try { 646 synchronized (this) { 647 ensureOpen(); 648 // Android-added: Lazy initialization of charOut and textOut. 649 BufferedWriter textOut = getTextOut(); 650 textOut.newLine(); 651 textOut.flushBuffer(); 652 charOut.flushBuffer(); 653 if (autoFlush) 654 out.flush(); 655 } 656 } 657 catch (InterruptedIOException x) { 658 Thread.currentThread().interrupt(); 659 } 660 catch (IOException x) { 661 trouble = true; 662 } 663 } 664 665 /* Methods that do not terminate lines */ 666 667 /** 668 * Prints a boolean value. The string produced by {@link 669 * java.lang.String#valueOf(boolean)} is translated into bytes 670 * according to the platform's default character encoding, and these bytes 671 * are written in exactly the manner of the 672 * {@link #write(int)} method. 673 * 674 * @param b The {@code boolean} to be printed 675 */ print(boolean b)676 public void print(boolean b) { 677 write(String.valueOf(b)); 678 } 679 680 /** 681 * Prints a character. The character is translated into one or more bytes 682 * according to the platform's default character encoding, and these bytes 683 * are written in exactly the manner of the 684 * {@link #write(int)} method. 685 * 686 * @param c The {@code char} to be printed 687 */ print(char c)688 public void print(char c) { 689 write(String.valueOf(c)); 690 } 691 692 /** 693 * Prints an integer. The string produced by {@link 694 * java.lang.String#valueOf(int)} is translated into bytes 695 * according to the platform's default character encoding, and these bytes 696 * are written in exactly the manner of the 697 * {@link #write(int)} method. 698 * 699 * @param i The {@code int} to be printed 700 * @see java.lang.Integer#toString(int) 701 */ print(int i)702 public void print(int i) { 703 write(String.valueOf(i)); 704 } 705 706 /** 707 * Prints a long integer. The string produced by {@link 708 * java.lang.String#valueOf(long)} is translated into bytes 709 * according to the platform's default character encoding, and these bytes 710 * are written in exactly the manner of the 711 * {@link #write(int)} method. 712 * 713 * @param l The {@code long} to be printed 714 * @see java.lang.Long#toString(long) 715 */ print(long l)716 public void print(long l) { 717 write(String.valueOf(l)); 718 } 719 720 /** 721 * Prints a floating-point number. The string produced by {@link 722 * java.lang.String#valueOf(float)} is translated into bytes 723 * according to the platform's default character encoding, and these bytes 724 * are written in exactly the manner of the 725 * {@link #write(int)} method. 726 * 727 * @param f The {@code float} to be printed 728 * @see java.lang.Float#toString(float) 729 */ print(float f)730 public void print(float f) { 731 write(String.valueOf(f)); 732 } 733 734 /** 735 * Prints a double-precision floating-point number. The string produced by 736 * {@link java.lang.String#valueOf(double)} is translated into 737 * bytes according to the platform's default character encoding, and these 738 * bytes are written in exactly the manner of the {@link 739 * #write(int)} method. 740 * 741 * @param d The {@code double} to be printed 742 * @see java.lang.Double#toString(double) 743 */ print(double d)744 public void print(double d) { 745 write(String.valueOf(d)); 746 } 747 748 /** 749 * Prints an array of characters. The characters are converted into bytes 750 * according to the platform's default character encoding, and these bytes 751 * are written in exactly the manner of the 752 * {@link #write(int)} method. 753 * 754 * @param s The array of chars to be printed 755 * 756 * @throws NullPointerException If {@code s} is {@code null} 757 */ print(char s[])758 public void print(char s[]) { 759 write(s); 760 } 761 762 /** 763 * Prints a string. If the argument is {@code null} then the string 764 * {@code "null"} is printed. Otherwise, the string's characters are 765 * converted into bytes according to the platform's default character 766 * encoding, and these bytes are written in exactly the manner of the 767 * {@link #write(int)} method. 768 * 769 * @param s The {@code String} to be printed 770 */ print(String s)771 public void print(String s) { 772 write(String.valueOf(s)); 773 } 774 775 /** 776 * Prints an object. The string produced by the {@link 777 * java.lang.String#valueOf(Object)} method is translated into bytes 778 * according to the platform's default character encoding, and these bytes 779 * are written in exactly the manner of the 780 * {@link #write(int)} method. 781 * 782 * @param obj The {@code Object} to be printed 783 * @see java.lang.Object#toString() 784 */ print(Object obj)785 public void print(Object obj) { 786 write(String.valueOf(obj)); 787 } 788 789 790 /* Methods that do terminate lines */ 791 792 /** 793 * Terminates the current line by writing the line separator string. The 794 * line separator string is defined by the system property 795 * {@code line.separator}, and is not necessarily a single newline 796 * character ({@code '\n'}). 797 */ println()798 public void println() { 799 newLine(); 800 } 801 802 /** 803 * Prints a boolean and then terminate the line. This method behaves as 804 * though it invokes {@link #print(boolean)} and then 805 * {@link #println()}. 806 * 807 * @param x The {@code boolean} to be printed 808 */ println(boolean x)809 public void println(boolean x) { 810 synchronized (this) { 811 print(x); 812 newLine(); 813 } 814 } 815 816 /** 817 * Prints a character and then terminate the line. This method behaves as 818 * though it invokes {@link #print(char)} and then 819 * {@link #println()}. 820 * 821 * @param x The {@code char} to be printed. 822 */ println(char x)823 public void println(char x) { 824 synchronized (this) { 825 print(x); 826 newLine(); 827 } 828 } 829 830 /** 831 * Prints an integer and then terminate the line. This method behaves as 832 * though it invokes {@link #print(int)} and then 833 * {@link #println()}. 834 * 835 * @param x The {@code int} to be printed. 836 */ println(int x)837 public void println(int x) { 838 synchronized (this) { 839 print(x); 840 newLine(); 841 } 842 } 843 844 /** 845 * Prints a long and then terminate the line. This method behaves as 846 * though it invokes {@link #print(long)} and then 847 * {@link #println()}. 848 * 849 * @param x a The {@code long} to be printed. 850 */ println(long x)851 public void println(long x) { 852 synchronized (this) { 853 print(x); 854 newLine(); 855 } 856 } 857 858 /** 859 * Prints a float and then terminate the line. This method behaves as 860 * though it invokes {@link #print(float)} and then 861 * {@link #println()}. 862 * 863 * @param x The {@code float} to be printed. 864 */ println(float x)865 public void println(float x) { 866 synchronized (this) { 867 print(x); 868 newLine(); 869 } 870 } 871 872 /** 873 * Prints a double and then terminate the line. This method behaves as 874 * though it invokes {@link #print(double)} and then 875 * {@link #println()}. 876 * 877 * @param x The {@code double} to be printed. 878 */ println(double x)879 public void println(double x) { 880 synchronized (this) { 881 print(x); 882 newLine(); 883 } 884 } 885 886 /** 887 * Prints an array of characters and then terminate the line. This method 888 * behaves as though it invokes {@link #print(char[])} and 889 * then {@link #println()}. 890 * 891 * @param x an array of chars to print. 892 */ println(char x[])893 public void println(char x[]) { 894 synchronized (this) { 895 print(x); 896 newLine(); 897 } 898 } 899 900 /** 901 * Prints a String and then terminate the line. This method behaves as 902 * though it invokes {@link #print(String)} and then 903 * {@link #println()}. 904 * 905 * @param x The {@code String} to be printed. 906 */ println(String x)907 public void println(String x) { 908 synchronized (this) { 909 print(x); 910 newLine(); 911 } 912 } 913 914 /** 915 * Prints an Object and then terminate the line. This method calls 916 * at first String.valueOf(x) to get the printed object's string value, 917 * then behaves as 918 * though it invokes {@link #print(String)} and then 919 * {@link #println()}. 920 * 921 * @param x The {@code Object} to be printed. 922 */ println(Object x)923 public void println(Object x) { 924 String s = String.valueOf(x); 925 synchronized (this) { 926 print(s); 927 newLine(); 928 } 929 } 930 931 932 /** 933 * A convenience method to write a formatted string to this output stream 934 * using the specified format string and arguments. 935 * 936 * <p> An invocation of this method of the form 937 * {@code out.printf(format, args)} behaves 938 * in exactly the same way as the invocation 939 * 940 * <pre>{@code 941 * out.format(format, args) 942 * }</pre> 943 * 944 * @param format 945 * A format string as described in <a 946 * href="../util/Formatter.html#syntax">Format string syntax</a> 947 * 948 * @param args 949 * Arguments referenced by the format specifiers in the format 950 * string. If there are more arguments than format specifiers, the 951 * extra arguments are ignored. The number of arguments is 952 * variable and may be zero. The maximum number of arguments is 953 * limited by the maximum dimension of a Java array as defined by 954 * <cite>The Java™ Virtual Machine Specification</cite>. 955 * The behaviour on a 956 * {@code null} argument depends on the <a 957 * href="../util/Formatter.html#syntax">conversion</a>. 958 * 959 * @throws java.util.IllegalFormatException 960 * If a format string contains an illegal syntax, a format 961 * specifier that is incompatible with the given arguments, 962 * insufficient arguments given the format string, or other 963 * illegal conditions. For specification of all possible 964 * formatting errors, see the <a 965 * href="../util/Formatter.html#detail">Details</a> section of the 966 * formatter class specification. 967 * 968 * @throws NullPointerException 969 * If the {@code format} is {@code null} 970 * 971 * @return This output stream 972 * 973 * @since 1.5 974 */ printf(String format, Object ... args)975 public PrintStream printf(String format, Object ... args) { 976 return format(format, args); 977 } 978 979 /** 980 * A convenience method to write a formatted string to this output stream 981 * using the specified format string and arguments. 982 * 983 * <p> An invocation of this method of the form 984 * {@code out.printf(l, format, args)} behaves 985 * in exactly the same way as the invocation 986 * 987 * <pre>{@code 988 * out.format(l, format, args) 989 * }</pre> 990 * 991 * @param l 992 * The {@linkplain java.util.Locale locale} to apply during 993 * formatting. If {@code l} is {@code null} then no localization 994 * is applied. 995 * 996 * @param format 997 * A format string as described in <a 998 * href="../util/Formatter.html#syntax">Format string syntax</a> 999 * 1000 * @param args 1001 * Arguments referenced by the format specifiers in the format 1002 * string. If there are more arguments than format specifiers, the 1003 * extra arguments are ignored. The number of arguments is 1004 * variable and may be zero. The maximum number of arguments is 1005 * limited by the maximum dimension of a Java array as defined by 1006 * <cite>The Java™ Virtual Machine Specification</cite>. 1007 * The behaviour on a 1008 * {@code null} argument depends on the <a 1009 * href="../util/Formatter.html#syntax">conversion</a>. 1010 * 1011 * @throws java.util.IllegalFormatException 1012 * If a format string contains an illegal syntax, a format 1013 * specifier that is incompatible with the given arguments, 1014 * insufficient arguments given the format string, or other 1015 * illegal conditions. For specification of all possible 1016 * formatting errors, see the <a 1017 * href="../util/Formatter.html#detail">Details</a> section of the 1018 * formatter class specification. 1019 * 1020 * @throws NullPointerException 1021 * If the {@code format} is {@code null} 1022 * 1023 * @return This output stream 1024 * 1025 * @since 1.5 1026 */ printf(Locale l, String format, Object ... args)1027 public PrintStream printf(Locale l, String format, Object ... args) { 1028 return format(l, format, args); 1029 } 1030 1031 /** 1032 * Writes a formatted string to this output stream using the specified 1033 * format string and arguments. 1034 * 1035 * <p> The locale always used is the one returned by {@link 1036 * java.util.Locale#getDefault(Locale.Category)} with 1037 * {@link java.util.Locale.Category#FORMAT FORMAT} category specified, 1038 * regardless of any previous invocations of other formatting methods on 1039 * this object. 1040 * 1041 * @param format 1042 * A format string as described in <a 1043 * href="../util/Formatter.html#syntax">Format string syntax</a> 1044 * 1045 * @param args 1046 * Arguments referenced by the format specifiers in the format 1047 * string. If there are more arguments than format specifiers, the 1048 * extra arguments are ignored. The number of arguments is 1049 * variable and may be zero. The maximum number of arguments is 1050 * limited by the maximum dimension of a Java array as defined by 1051 * <cite>The Java™ Virtual Machine Specification</cite>. 1052 * The behaviour on a 1053 * {@code null} argument depends on the <a 1054 * href="../util/Formatter.html#syntax">conversion</a>. 1055 * 1056 * @throws java.util.IllegalFormatException 1057 * If a format string contains an illegal syntax, a format 1058 * specifier that is incompatible with the given arguments, 1059 * insufficient arguments given the format string, or other 1060 * illegal conditions. For specification of all possible 1061 * formatting errors, see the <a 1062 * href="../util/Formatter.html#detail">Details</a> section of the 1063 * formatter class specification. 1064 * 1065 * @throws NullPointerException 1066 * If the {@code format} is {@code null} 1067 * 1068 * @return This output stream 1069 * 1070 * @since 1.5 1071 */ format(String format, Object ... args)1072 public PrintStream format(String format, Object ... args) { 1073 try { 1074 synchronized (this) { 1075 ensureOpen(); 1076 if ((formatter == null) 1077 || (formatter.locale() != 1078 Locale.getDefault(Locale.Category.FORMAT))) 1079 formatter = new Formatter((Appendable) this); 1080 formatter.format(Locale.getDefault(Locale.Category.FORMAT), 1081 format, args); 1082 } 1083 } catch (InterruptedIOException x) { 1084 Thread.currentThread().interrupt(); 1085 } catch (IOException x) { 1086 trouble = true; 1087 } 1088 return this; 1089 } 1090 1091 /** 1092 * Writes a formatted string to this output stream using the specified 1093 * format string and arguments. 1094 * 1095 * @param l 1096 * The {@linkplain java.util.Locale locale} to apply during 1097 * formatting. If {@code l} is {@code null} then no localization 1098 * is applied. 1099 * 1100 * @param format 1101 * A format string as described in <a 1102 * href="../util/Formatter.html#syntax">Format string syntax</a> 1103 * 1104 * @param args 1105 * Arguments referenced by the format specifiers in the format 1106 * string. If there are more arguments than format specifiers, the 1107 * extra arguments are ignored. The number of arguments is 1108 * variable and may be zero. The maximum number of arguments is 1109 * limited by the maximum dimension of a Java array as defined by 1110 * <cite>The Java™ Virtual Machine Specification</cite>. 1111 * The behaviour on a 1112 * {@code null} argument depends on the <a 1113 * href="../util/Formatter.html#syntax">conversion</a>. 1114 * 1115 * @throws java.util.IllegalFormatException 1116 * If a format string contains an illegal syntax, a format 1117 * specifier that is incompatible with the given arguments, 1118 * insufficient arguments given the format string, or other 1119 * illegal conditions. For specification of all possible 1120 * formatting errors, see the <a 1121 * href="../util/Formatter.html#detail">Details</a> section of the 1122 * formatter class specification. 1123 * 1124 * @throws NullPointerException 1125 * If the {@code format} is {@code null} 1126 * 1127 * @return This output stream 1128 * 1129 * @since 1.5 1130 */ format(Locale l, String format, Object ... args)1131 public PrintStream format(Locale l, String format, Object ... args) { 1132 try { 1133 synchronized (this) { 1134 ensureOpen(); 1135 if ((formatter == null) 1136 || (formatter.locale() != l)) 1137 formatter = new Formatter(this, l); 1138 formatter.format(l, format, args); 1139 } 1140 } catch (InterruptedIOException x) { 1141 Thread.currentThread().interrupt(); 1142 } catch (IOException x) { 1143 trouble = true; 1144 } 1145 return this; 1146 } 1147 1148 /** 1149 * Appends the specified character sequence to this output stream. 1150 * 1151 * <p> An invocation of this method of the form {@code out.append(csq)} 1152 * behaves in exactly the same way as the invocation 1153 * 1154 * <pre>{@code 1155 * out.print(csq.toString()) 1156 * }</pre> 1157 * 1158 * <p> Depending on the specification of {@code toString} for the 1159 * character sequence {@code csq}, the entire sequence may not be 1160 * appended. For instance, invoking then {@code toString} method of a 1161 * character buffer will return a subsequence whose content depends upon 1162 * the buffer's position and limit. 1163 * 1164 * @param csq 1165 * The character sequence to append. If {@code csq} is 1166 * {@code null}, then the four characters {@code "null"} are 1167 * appended to this output stream. 1168 * 1169 * @return This output stream 1170 * 1171 * @since 1.5 1172 */ append(CharSequence csq)1173 public PrintStream append(CharSequence csq) { 1174 print(String.valueOf(csq)); 1175 return this; 1176 } 1177 1178 /** 1179 * Appends a subsequence of the specified character sequence to this output 1180 * stream. 1181 * 1182 * <p> An invocation of this method of the form 1183 * {@code out.append(csq, start, end)} when 1184 * {@code csq} is not {@code null}, behaves in 1185 * exactly the same way as the invocation 1186 * 1187 * <pre>{@code 1188 * out.print(csq.subSequence(start, end).toString()) 1189 * }</pre> 1190 * 1191 * @param csq 1192 * The character sequence from which a subsequence will be 1193 * appended. If {@code csq} is {@code null}, then characters 1194 * will be appended as if {@code csq} contained the four 1195 * characters {@code "null"}. 1196 * 1197 * @param start 1198 * The index of the first character in the subsequence 1199 * 1200 * @param end 1201 * The index of the character following the last character in the 1202 * subsequence 1203 * 1204 * @return This output stream 1205 * 1206 * @throws IndexOutOfBoundsException 1207 * If {@code start} or {@code end} are negative, {@code start} 1208 * is greater than {@code end}, or {@code end} is greater than 1209 * {@code csq.length()} 1210 * 1211 * @since 1.5 1212 */ append(CharSequence csq, int start, int end)1213 public PrintStream append(CharSequence csq, int start, int end) { 1214 if (csq == null) csq = "null"; 1215 return append(csq.subSequence(start, end)); 1216 } 1217 1218 /** 1219 * Appends the specified character to this output stream. 1220 * 1221 * <p> An invocation of this method of the form {@code out.append(c)} 1222 * behaves in exactly the same way as the invocation 1223 * 1224 * <pre>{@code 1225 * out.print(c) 1226 * }</pre> 1227 * 1228 * @param c 1229 * The 16-bit character to append 1230 * 1231 * @return This output stream 1232 * 1233 * @since 1.5 1234 */ append(char c)1235 public PrintStream append(char c) { 1236 print(c); 1237 return this; 1238 } 1239 1240 } 1241