String vs StringBuffer vs StringBuilder
- 20th Jan 2018
- 1
- 11943
- difference between string and stringbuffer and stringbuffer in java difference between string and stringbuffer in java difference between string and stringbuilder in java difference between stringbuffer and stringbuffer in java which is better string or stringbuilder or stringbuffer ?
We know that, String is one of the most frequently used class in Java programming.
Many java programmers are not aware of the fact that String is immutable in java which means every modification to a string creates a new String.
Modification could be concatenation of string with other string or converting string to lower case or trimming the string to remove spaces.
In all these scenarios, String creates a new object.
If you think of any solution in Java where any modification to string should not create new String object rather it has to modify the same string.
Solution for the same is either StringBuffer or StringBuilder
Lets see the difference between String,StringBuilder and StringBuffer
1) Object creation
String can be created in 2 ways , either using new or by string literal in double quotes where as StringBuffer and StringBuilder object has to be created using “new” only.
Example:
- class StringBufferBuilder1 {
- public static void main(String args[]){
- String s1= new String("java");
- String s2= "simple";
- StringBuffer buffer= new StringBuffer("java");
- StringBuilder builder= new StringBuilder("java ");
- }
- }
class StringBufferBuilder1 { public static void main(String args[]){ String s1= new String("java"); String s2= "simple"; StringBuffer buffer= new StringBuffer("java"); StringBuilder builder= new StringBuilder("java "); } }
2) Immutability
String is immutable and hence it creates new object for each modification
Whereas StringBuffer and StringBuilder are mutable
which means same string will be modified for every modification of string.
Example:
- class StringBufferBuilder1 {
- public static void main(String args[]){
- String s= new String("java ");
- s.concat("in simple way");
- System.out.println(s);
- StringBuffer buffer= new StringBuffer("java ");
- buffer.append("in simple way");
- System.out.println(buffer);
- StringBuilder builder= new StringBuilder("java ");
- builder.append("in simple way");
- System.out.println(builder);
- }
- }
class StringBufferBuilder1 { public static void main(String args[]){ String s= new String("java "); s.concat("in simple way"); System.out.println(s); StringBuffer buffer= new StringBuffer("java "); buffer.append("in simple way"); System.out.println(buffer); StringBuilder builder= new StringBuilder("java "); builder.append("in simple way"); System.out.println(builder); } }
We can see that , in case of string when we perform concatenation using concat() method,it creates a new string object and its not pointed by any reference variable and variable “s” is still pointing to old string “java”.
Whereas in case of StringBuffer and StringBuilder, concat() method just modifies the same string object and hence concatenated result is displayed for them.
3) Thread safety
String is always thread safety because of its immutability feature.
It should be preferred only if there is no frequent modification, otherwise we will end up with lot of memory leakage.
As an alternative in that case, we can choose StringBuffer or StringBulder based on single threaded or multithreaded application
StringBuffer is mutable and thread safety as all the methods of this class are synchronized, so we should prefer to use it in multithreaded application
StringBuilder is mutable but not thread safe as methods of this class are not synchronized, so we should prefer to use it in single threaded application.
4) Performace
Performance of StringBuilder is far better compared to String and StringBuffer.
Consider the below code
- class StringBufferBuilder2 {
- public static void main(String args[]){
- String[] stringArray = {"java","in","simple","way"};
- String result = "";
- for (String s : stringArray) {
- result = result + s;
- }
- StringBuilder builder = new StringBuilder();
- for (String s : stringArray) {
- builder.append(s);
- }
- String result = builder.toString();
- StringBuffer buffer = new StringBuffer();
- for (String s : stringArray) {
- buffer.append(s);
- }
- String result = buffer.toString();
- }
- }
class StringBufferBuilder2 { public static void main(String args[]){ String[] stringArray = {"java","in","simple","way"}; String result = ""; for (String s : stringArray) { result = result + s; } StringBuilder builder = new StringBuilder(); for (String s : stringArray) { builder.append(s); } String result = builder.toString(); StringBuffer buffer = new StringBuffer(); for (String s : stringArray) { buffer.append(s); } String result = buffer.toString(); } }
In this code, we are trying to perform concatenation inside a loop.
Performance of String will not be good here as it has to create new string for each iteration.
Performance of StringBuilder and StringBuffer will be very good compared to String as they alter the same string for each iteration without crating new object.
Between StringBuilder and StringBuffer, StringBuilder will be giving better performance as its not synchronized.
Yes, if methods are synchronized,there will be a little performance overhead.
5) hashcode and equals methods
String class has overridden hashcode() and equals() methods and 2 strings are considered as equals if their hashcode is same
and also equals() method returns true.
StringBuilder and StringBuffer classes have not overridden hashcode() and equals() methods.
And it’s because they are mutable, and their primary use is for constructing strings.
If we need to compare content,we can call StringBuffer#toString() or StringBuilder#toString() and compare the returned value.
Consider below example
- class StringBufferBuilder3 {
- public static void main(String args[]){
- String s1 = new String("java");
- String s2 = new String("java");
- System.out.println(s1.equals(s2));
- StringBuilder builder1 = new StringBuilder ("java");
- StringBuilder builder2 = new StringBuilder ("java");
- System.out.println(builder1.equals(builder2));
- StringBuffer buffer1= new StringBuffer ("java");
- StringBuffer buffer2 = new StringBuffer ("java");
- System.out.println(buffer1.equals(buffer2));
- }
- }
class StringBufferBuilder3 { public static void main(String args[]){ String s1 = new String("java"); String s2 = new String("java"); System.out.println(s1.equals(s2)); StringBuilder builder1 = new StringBuilder ("java"); StringBuilder builder2 = new StringBuilder ("java"); System.out.println(builder1.equals(builder2)); StringBuffer buffer1= new StringBuffer ("java"); StringBuffer buffer2 = new StringBuffer ("java"); System.out.println(buffer1.equals(buffer2)); } }
We can see that, though the content is same
for both the objects, StringBuffer and StringBuilder returned false
for equals() method
Note:
String is immutable but StringBuilder and StringBuffer are mutable
StringBuilder is not synchronized and StringBuffer is synchronized, hence StringBuilder is faster.
We can use String if we need immutability and if we have less modifications
We can use StringBuilder for mutable string without thread safety
We can use StringBuffer for mutable string with thread safety
Note down all these points to choose the right candidate in your application among String, StringBuffer and StringBuilder.
awesome