1 /* 2 * Copyright (c) 1994, 2013, 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.lang; 27 28 import java.util.Arrays; 29 30 /** 31 * A thread-safe, mutable sequence of characters. 32 * A string buffer is like a {@link String}, but can be modified. At any 33 * point in time it contains some particular sequence of characters, but 34 * the length and content of the sequence can be changed through certain 35 * method calls. 36 * <p> 37 * String buffers are safe for use by multiple threads. The methods 38 * are synchronized where necessary so that all the operations on any 39 * particular instance behave as if they occur in some serial order 40 * that is consistent with the order of the method calls made by each of 41 * the individual threads involved. 42 * <p> 43 * The principal operations on a {@code StringBuffer} are the 44 * {@code append} and {@code insert} methods, which are 45 * overloaded so as to accept data of any type. Each effectively 46 * converts a given datum to a string and then appends or inserts the 47 * characters of that string to the string buffer. The 48 * {@code append} method always adds these characters at the end 49 * of the buffer; the {@code insert} method adds the characters at 50 * a specified point. 51 * <p> 52 * For example, if {@code z} refers to a string buffer object 53 * whose current contents are {@code "start"}, then 54 * the method call {@code z.append("le")} would cause the string 55 * buffer to contain {@code "startle"}, whereas 56 * {@code z.insert(4, "le")} would alter the string buffer to 57 * contain {@code "starlet"}. 58 * <p> 59 * In general, if sb refers to an instance of a {@code StringBuffer}, 60 * then {@code sb.append(x)} has the same effect as 61 * {@code sb.insert(sb.length(), x)}. 62 * <p> 63 * Whenever an operation occurs involving a source sequence (such as 64 * appending or inserting from a source sequence), this class synchronizes 65 * only on the string buffer performing the operation, not on the source. 66 * Note that while {@code StringBuffer} is designed to be safe to use 67 * concurrently from multiple threads, if the constructor or the 68 * {@code append} or {@code insert} operation is passed a source sequence 69 * that is shared across threads, the calling code must ensure 70 * that the operation has a consistent and unchanging view of the source 71 * sequence for the duration of the operation. 72 * This could be satisfied by the caller holding a lock during the 73 * operation's call, by using an immutable source sequence, or by not 74 * sharing the source sequence across threads. 75 * <p> 76 * Every string buffer has a capacity. As long as the length of the 77 * character sequence contained in the string buffer does not exceed 78 * the capacity, it is not necessary to allocate a new internal 79 * buffer array. If the internal buffer overflows, it is 80 * automatically made larger. 81 * <p> 82 * Unless otherwise noted, passing a {@code null} argument to a constructor 83 * or method in this class will cause a {@link NullPointerException} to be 84 * thrown. 85 * <p> 86 * As of release JDK 5, this class has been supplemented with an equivalent 87 * class designed for use by a single thread, {@link StringBuilder}. The 88 * {@code StringBuilder} class should generally be used in preference to 89 * this one, as it supports all of the same operations but it is faster, as 90 * it performs no synchronization. 91 * 92 * @author Arthur van Hoff 93 * @see java.lang.StringBuilder 94 * @see java.lang.String 95 * @since 1.0 96 */ 97 public final class StringBuffer 98 extends AbstractStringBuilder 99 implements java.io.Serializable, CharSequence 100 { 101 102 /** 103 * A cache of the last value returned by toString. Cleared 104 * whenever the StringBuffer is modified. 105 */ 106 private transient char[] toStringCache; 107 108 /** use serialVersionUID from JDK 1.0.2 for interoperability */ 109 static final long serialVersionUID = 3388685877147921107L; 110 111 /** 112 * Constructs a string buffer with no characters in it and an 113 * initial capacity of 16 characters. 114 */ 115 public StringBuffer() { 116 super(16); 117 } 118 119 /** 120 * Constructs a string buffer with no characters in it and 121 * the specified initial capacity. 122 * 123 * @param capacity the initial capacity. 124 * @exception NegativeArraySizeException if the {@code capacity} 125 * argument is less than {@code 0}. 126 */ 127 public StringBuffer(int capacity) { 128 super(capacity); 129 } 130 131 /** 132 * Constructs a string buffer initialized to the contents of the 133 * specified string. The initial capacity of the string buffer is 134 * {@code 16} plus the length of the string argument. 135 * 136 * @param str the initial contents of the buffer. 137 */ 138 public StringBuffer(String str) { 139 super(str.length() + 16); 140 append(str); 141 } 142 143 /** 144 * Constructs a string buffer that contains the same characters 145 * as the specified {@code CharSequence}. The initial capacity of 146 * the string buffer is {@code 16} plus the length of the 147 * {@code CharSequence} argument. 148 * <p> 149 * If the length of the specified {@code CharSequence} is 150 * less than or equal to zero, then an empty buffer of capacity 151 * {@code 16} is returned. 152 * 153 * @param seq the sequence to copy. 154 * @since 1.5 155 */ 156 public StringBuffer(CharSequence seq) { 157 this(seq.length() + 16); 158 append(seq); 159 } 160 161 @Override 162 public synchronized int length() { 163 return count; 164 } 165 166 @Override 167 public synchronized int capacity() { 168 return value.length; 169 } 170 171 172 @Override 173 public synchronized void ensureCapacity(int minimumCapacity) { 174 if (minimumCapacity > value.length) { 175 expandCapacity(minimumCapacity); 176 } 177 } 178 179 /** 180 * @since 1.5 181 */ 182 @Override 183 public synchronized void trimToSize() { 184 super.trimToSize(); 185 } 186 187 /** 188 * @throws IndexOutOfBoundsException {@inheritDoc} 189 * @see #length() 190 */ 191 @Override 192 public synchronized void setLength(int newLength) { 193 toStringCache = null; 194 super.setLength(newLength); 195 } 196 197 /** 198 * @throws IndexOutOfBoundsException {@inheritDoc} 199 * @see #length() 200 */ 201 @Override 202 public synchronized char charAt(int index) { 203 if ((index < 0) || (index >= count)) 204 throw new StringIndexOutOfBoundsException(index); 205 return value[index]; 206 } 207 208 /** 209 * @throws IndexOutOfBoundsException {@inheritDoc} 210 * @since 1.5 211 */ 212 @Override 213 public synchronized int codePointAt(int index) { 214 return super.codePointAt(index); 215 } 216 217 /** 218 * @throws IndexOutOfBoundsException {@inheritDoc} 219 * @since 1.5 220 */ 221 @Override 222 public synchronized int codePointBefore(int index) { 223 return super.codePointBefore(index); 224 } 225 226 /** 227 * @throws IndexOutOfBoundsException {@inheritDoc} 228 * @since 1.5 229 */ 230 @Override 231 public synchronized int codePointCount(int beginIndex, int endIndex) { 232 return super.codePointCount(beginIndex, endIndex); 233 } 234 235 /** 236 * @throws IndexOutOfBoundsException {@inheritDoc} 237 * @since 1.5 238 */ 239 @Override 240 public synchronized int offsetByCodePoints(int index, int codePointOffset) { 241 return super.offsetByCodePoints(index, codePointOffset); 242 } 243 244 /** 245 * @throws IndexOutOfBoundsException {@inheritDoc} 246 */ 247 @Override 248 public synchronized void getChars(int srcBegin, int srcEnd, char[] dst, 249 int dstBegin) 250 { 251 super.getChars(srcBegin, srcEnd, dst, dstBegin); 252 } 253 254 /** 255 * @throws IndexOutOfBoundsException {@inheritDoc} 256 * @see #length() 257 */ 258 @Override 259 public synchronized void setCharAt(int index, char ch) { 260 if ((index < 0) || (index >= count)) 261 throw new StringIndexOutOfBoundsException(index); 262 toStringCache = null; 263 value[index] = ch; 264 } 265 266 @Override 267 public synchronized StringBuffer append(Object obj) { 268 toStringCache = null; 269 super.append(String.valueOf(obj)); 270 return this; 271 } 272 273 @Override 274 public synchronized StringBuffer append(String str) { 275 toStringCache = null; 276 super.append(str); 277 return this; 278 } 279 280 /** 281 * Appends the specified {@code StringBuffer} to this sequence. 282 * <p> 283 * The characters of the {@code StringBuffer} argument are appended, 284 * in order, to the contents of this {@code StringBuffer}, increasing the 285 * length of this {@code StringBuffer} by the length of the argument. 286 * If {@code sb} is {@code null}, then the four characters 287 * {@code "null"} are appended to this {@code StringBuffer}. 288 * <p> 289 * Let <i>n</i> be the length of the old character sequence, the one 290 * contained in the {@code StringBuffer} just prior to execution of the 291 * {@code append} method. Then the character at index <i>k</i> in 292 * the new character sequence is equal to the character at index <i>k</i> 293 * in the old character sequence, if <i>k</i> is less than <i>n</i>; 294 * otherwise, it is equal to the character at index <i>k-n</i> in the 295 * argument {@code sb}. 296 * <p> 297 * This method synchronizes on {@code this}, the destination 298 * object, but does not synchronize on the source ({@code sb}). 299 * 300 * @param sb the {@code StringBuffer} to append. 301 * @return a reference to this object. 302 * @since 1.4 303 */ 304 public synchronized StringBuffer append(StringBuffer sb) { 305 toStringCache = null; 306 super.append(sb); 307 return this; 308 } 309 310 /** 311 * @since 1.8 312 */ 313 @Override 314 synchronized StringBuffer append(AbstractStringBuilder asb) { 315 toStringCache = null; 316 super.append(asb); 317 return this; 318 } 319 320 /** 321 * Appends the specified {@code CharSequence} to this 322 * sequence. 323 * <p> 324 * The characters of the {@code CharSequence} argument are appended, 325 * in order, increasing the length of this sequence by the length of the 326 * argument. 327 * 328 * <p>The result of this method is exactly the same as if it were an 329 * invocation of this.append(s, 0, s.length()); 330 * 331 * <p>This method synchronizes on {@code this}, the destination 332 * object, but does not synchronize on the source ({@code s}). 333 * 334 * <p>If {@code s} is {@code null}, then the four characters 335 * {@code "null"} are appended. 336 * 337 * @param s the {@code CharSequence} to append. 338 * @return a reference to this object. 339 * @since 1.5 340 */ 341 @Override 342 public synchronized StringBuffer append(CharSequence s) { 343 toStringCache = null; 344 super.append(s); 345 return this; 346 } 347 348 /** 349 * @throws IndexOutOfBoundsException {@inheritDoc} 350 * @since 1.5 351 */ 352 @Override 353 public synchronized StringBuffer append(CharSequence s, int start, int end) 354 { 355 toStringCache = null; 356 super.append(s, start, end); 357 return this; 358 } 359 360 @Override 361 public synchronized StringBuffer append(char[] str) { 362 toStringCache = null; 363 super.append(str); 364 return this; 365 } 366 367 /** 368 * @throws IndexOutOfBoundsException {@inheritDoc} 369 */ 370 @Override 371 public synchronized StringBuffer append(char[] str, int offset, int len) { 372 toStringCache = null; 373 super.append(str, offset, len); 374 return this; 375 } 376 377 @Override 378 public synchronized StringBuffer append(boolean b) { 379 toStringCache = null; 380 super.append(b); 381 return this; 382 } 383 384 @Override 385 public synchronized StringBuffer append(char c) { 386 toStringCache = null; 387 super.append(c); 388 return this; 389 } 390 391 @Override 392 public synchronized StringBuffer append(int i) { 393 toStringCache = null; 394 super.append(i); 395 return this; 396 } 397 398 /** 399 * @since 1.5 400 */ 401 @Override 402 public synchronized StringBuffer appendCodePoint(int codePoint) { 403 toStringCache = null; 404 super.appendCodePoint(codePoint); 405 return this; 406 } 407 408 @Override 409 public synchronized StringBuffer append(long lng) { 410 toStringCache = null; 411 super.append(lng); 412 return this; 413 } 414 415 @Override 416 public synchronized StringBuffer append(float f) { 417 toStringCache = null; 418 super.append(f); 419 return this; 420 } 421 422 @Override 423 public synchronized StringBuffer append(double d) { 424 toStringCache = null; 425 super.append(d); 426 return this; 427 } 428 429 /** 430 * @throws StringIndexOutOfBoundsException {@inheritDoc} 431 * @since 1.2 432 */ 433 @Override 434 public synchronized StringBuffer delete(int start, int end) { 435 toStringCache = null; 436 super.delete(start, end); 437 return this; 438 } 439 440 /** 441 * @throws StringIndexOutOfBoundsException {@inheritDoc} 442 * @since 1.2 443 */ 444 @Override 445 public synchronized StringBuffer deleteCharAt(int index) { 446 toStringCache = null; 447 super.deleteCharAt(index); 448 return this; 449 } 450 451 /** 452 * @throws StringIndexOutOfBoundsException {@inheritDoc} 453 * @since 1.2 454 */ 455 @Override 456 public synchronized StringBuffer replace(int start, int end, String str) { 457 toStringCache = null; 458 super.replace(start, end, str); 459 return this; 460 } 461 462 /** 463 * @throws StringIndexOutOfBoundsException {@inheritDoc} 464 * @since 1.2 465 */ 466 @Override 467 public synchronized String substring(int start) { 468 return substring(start, count); 469 } 470 471 /** 472 * @throws IndexOutOfBoundsException {@inheritDoc} 473 * @since 1.4 474 */ 475 @Override 476 public synchronized CharSequence subSequence(int start, int end) { 477 return super.substring(start, end); 478 } 479 480 /** 481 * @throws StringIndexOutOfBoundsException {@inheritDoc} 482 * @since 1.2 483 */ 484 @Override 485 public synchronized String substring(int start, int end) { 486 return super.substring(start, end); 487 } 488 489 /** 490 * @throws StringIndexOutOfBoundsException {@inheritDoc} 491 * @since 1.2 492 */ 493 @Override 494 public synchronized StringBuffer insert(int index, char[] str, int offset, 495 int len) 496 { 497 toStringCache = null; 498 super.insert(index, str, offset, len); 499 return this; 500 } 501 502 /** 503 * @throws StringIndexOutOfBoundsException {@inheritDoc} 504 */ 505 @Override 506 public synchronized StringBuffer insert(int offset, Object obj) { 507 toStringCache = null; 508 super.insert(offset, String.valueOf(obj)); 509 return this; 510 } 511 512 /** 513 * @throws StringIndexOutOfBoundsException {@inheritDoc} 514 */ 515 @Override 516 public synchronized StringBuffer insert(int offset, String str) { 517 toStringCache = null; 518 super.insert(offset, str); 519 return this; 520 } 521 522 /** 523 * @throws StringIndexOutOfBoundsException {@inheritDoc} 524 */ 525 @Override 526 public synchronized StringBuffer insert(int offset, char[] str) { 527 toStringCache = null; 528 super.insert(offset, str); 529 return this; 530 } 531 532 /** 533 * @throws IndexOutOfBoundsException {@inheritDoc} 534 * @since 1.5 535 */ 536 @Override 537 public StringBuffer insert(int dstOffset, CharSequence s) { 538 // Note, synchronization achieved via invocations of other StringBuffer methods 539 // after narrowing of s to specific type 540 // Ditto for toStringCache clearing 541 super.insert(dstOffset, s); 542 return this; 543 } 544 545 /** 546 * @throws IndexOutOfBoundsException {@inheritDoc} 547 * @since 1.5 548 */ 549 @Override 550 public synchronized StringBuffer insert(int dstOffset, CharSequence s, 551 int start, int end) 552 { 553 toStringCache = null; 554 super.insert(dstOffset, s, start, end); 555 return this; 556 } 557 558 /** 559 * @throws StringIndexOutOfBoundsException {@inheritDoc} 560 */ 561 @Override 562 public StringBuffer insert(int offset, boolean b) { 563 // Note, synchronization achieved via invocation of StringBuffer insert(int, String) 564 // after conversion of b to String by super class method 565 // Ditto for toStringCache clearing 566 super.insert(offset, b); 567 return this; 568 } 569 570 /** 571 * @throws IndexOutOfBoundsException {@inheritDoc} 572 */ 573 @Override 574 public synchronized StringBuffer insert(int offset, char c) { 575 toStringCache = null; 576 super.insert(offset, c); 577 return this; 578 } 579 580 /** 581 * @throws StringIndexOutOfBoundsException {@inheritDoc} 582 */ 583 @Override 584 public StringBuffer insert(int offset, int i) { 585 // Note, synchronization achieved via invocation of StringBuffer insert(int, String) 586 // after conversion of i to String by super class method 587 // Ditto for toStringCache clearing 588 super.insert(offset, i); 589 return this; 590 } 591 592 /** 593 * @throws StringIndexOutOfBoundsException {@inheritDoc} 594 */ 595 @Override 596 public StringBuffer insert(int offset, long l) { 597 // Note, synchronization achieved via invocation of StringBuffer insert(int, String) 598 // after conversion of l to String by super class method 599 // Ditto for toStringCache clearing 600 super.insert(offset, l); 601 return this; 602 } 603 604 /** 605 * @throws StringIndexOutOfBoundsException {@inheritDoc} 606 */ 607 @Override 608 public StringBuffer insert(int offset, float f) { 609 // Note, synchronization achieved via invocation of StringBuffer insert(int, String) 610 // after conversion of f to String by super class method 611 // Ditto for toStringCache clearing 612 super.insert(offset, f); 613 return this; 614 } 615 616 /** 617 * @throws StringIndexOutOfBoundsException {@inheritDoc} 618 */ 619 @Override 620 public StringBuffer insert(int offset, double d) { 621 // Note, synchronization achieved via invocation of StringBuffer insert(int, String) 622 // after conversion of d to String by super class method 623 // Ditto for toStringCache clearing 624 super.insert(offset, d); 625 return this; 626 } 627 628 /** 629 * @since 1.4 630 */ 631 @Override 632 public int indexOf(String str) { 633 // Note, synchronization achieved via invocations of other StringBuffer methods 634 return super.indexOf(str); 635 } 636 637 /** 638 * @since 1.4 639 */ 640 @Override 641 public synchronized int indexOf(String str, int fromIndex) { 642 return super.indexOf(str, fromIndex); 643 } 644 645 /** 646 * @since 1.4 647 */ 648 @Override 649 public int lastIndexOf(String str) { 650 // Note, synchronization achieved via invocations of other StringBuffer methods 651 return lastIndexOf(str, count); 652 } 653 654 /** 655 * @since 1.4 656 */ 657 @Override 658 public synchronized int lastIndexOf(String str, int fromIndex) { 659 return super.lastIndexOf(str, fromIndex); 660 } 661 662 /** 663 * @since 1.0.2 664 */ 665 @Override 666 public synchronized StringBuffer reverse() { 667 toStringCache = null; 668 super.reverse(); 669 return this; 670 } 671 672 @Override 673 public synchronized String toString() { 674 if (toStringCache == null) { 675 toStringCache = Arrays.copyOfRange(value, 0, count); 676 } 677 return new String(toStringCache, true); 678 } 679 680 /** 681 * Serializable fields for StringBuffer. 682 * 683 * @serialField value char[] 684 * The backing character array of this StringBuffer. 685 * @serialField count int 686 * The number of characters in this StringBuffer. 687 * @serialField shared boolean 688 * A flag indicating whether the backing array is shared. 689 * The value is ignored upon deserialization. 690 */ 691 private static final java.io.ObjectStreamField[] serialPersistentFields = 692 { 693 new java.io.ObjectStreamField("value", char[].class), 694 new java.io.ObjectStreamField("count", Integer.TYPE), 695 new java.io.ObjectStreamField("shared", Boolean.TYPE), 696 }; 697 698 /** 699 * readObject is called to restore the state of the StringBuffer from 700 * a stream. 701 */ 702 private synchronized void writeObject(java.io.ObjectOutputStream s) 703 throws java.io.IOException { 704 java.io.ObjectOutputStream.PutField fields = s.putFields(); 705 fields.put("value", value); 706 fields.put("count", count); 707 fields.put("shared", false); 708 s.writeFields(); 709 } 710 711 /** 712 * readObject is called to restore the state of the StringBuffer from 713 * a stream. 714 */ 715 private void readObject(java.io.ObjectInputStream s) 716 throws java.io.IOException, ClassNotFoundException { 717 java.io.ObjectInputStream.GetField fields = s.readFields(); 718 value = (char[])fields.get("value", null); 719 count = fields.get("count", 0); 720 } 721 }