The advantage of String being immutable in java are listed below:
The String literals are being cached in the String Pool which saves a lot of space in the heap memory.
As immutability assures that the internal state of the object remains constant after it has been created, so when the object is assigned to a variable so we cannot modify it in any way. So we can consider using String for security systems for creating username, connection URL's, password etc.
It also makes it thread-safe thereby improving the performance by eliminating the use of synchronization.
Hashcode can be cached because the value of String doesn't change, so hashcode remains the same.
Immutability provides assurance that the correct class is getting loaded by Classloader. So, String is used by Classloaders.
A string pool is a memory space allocated in the java heap.
When we create a String using double quotes, JVM looks in the String pool to find if any other String is stored with the same value. If found, it just returns the reference to that String object else it creates a new String object with a given value and stores it in the String pool.
When you create a new string like this:
String s1 = “one”
JVM automatically checks if the same value exists in the string constant pool or not.
if yes, it occupies the already existing value.
If no, it creates a new string by itself and adds it to the string pool.
If you want to halt this behaviour, create a string using a new operator:
String s2 = new String(“two”)
String s3 = new String(“one”)
Now, if you are willing to add this string to the string literal pool, Java provides you with a method called the intern() method; you can call the native intern() method like this:
String s4 = s3.intern();
This diagram explains how String is stored in memory.
StringJoiner is used to join a sequence of characters separated by a delimiter like taking a list of items and returning them as a delimited string. It can also create the string starting with a supplied prefix and ending with a supplied suffix but that is optional.
StringJoiner newString = new StringJoiner(",", "[", "]");
newString.add("Item 1");
newString.add("Item 2");
newString.add("Item 3");
System.out.println(joiner.toString());
//Returns [Item 1, Item 2, Item 3]
The following methods are available in StringJoiner class:
StringJoiner add(CharSequence element) - A copy of the given CharSequence value is added as the next element of the StringJoiner value. "null" is added if the element is null.
String toString() - This method returns the String object of this StringJoiner. It overrides the toString in class Object.
int length() - This method returns the length of the String of the StringJoiner.
StringJoiner setEmptyValue(CharSequence emptyVal) - It sets the characters to be returned as the value of an empty StringJoiner.If the emptyVal parameter is null, it throws NullPointerException.
StringJoiner merge(StringJoiner input) - It adds the contents of the given StringJoiner without the next element if it is non-empty.
String Interning is a method of storing only one copy of each distinct String Value, which must be immutable.
By applying String.intern() on a couple of strings will ensure that all strings having the same contents share the same memory
For example
String s1 = “one”;
String s3 = new String(“one”);
Now, if you are willing to add this string to the string literal pool, Java provides you with a method called the intern() method; you can call the native intern() method like this:
String s4 = s3.intern();
Both StringBuffer and StringBuilder are mutable classes.
StringBuilder operations are not thread-safe whereas StringBuffer operations are thread-safe and synchronized and are suggested for the multithreaded environment.
Speed and Performance of StringBuffer is faster because synchronization is not involved in it.
package stringmanipulation;
import java.util.LinkedHashMap;
import java.util.Map;
public class FirstNonRepeatingCharInString {
public static void main(String[] args) {
firstNonRepChar("CodeRovers Duo");
}
private static void firstNonRepChar(String string) {
//Using a LinkedHashMap to preserve the insertion order.
//Creating a Map that would store <Alphabet ,Its Count>
Map<String, Integer> myMap = new LinkedHashMap<String, Integer>();
//Looping through the characters of the string
for (int i = 0; i < string.length(); i++) {
String key = (string.charAt(i) + "").toLowerCase();
//Checking if the map already contains the alphabet
if (myMap.keySet().contains(key)) {
//Increasing the count by 1
myMap.put(key, myMap.get(key) + 1);
} else {
//Setting the count of the alphabet to 1
myMap.put(key, 1);
}
}
//Iterating through the Map
for (String s : myMap.keySet()) {
if (myMap.get(s) == 1) {
System.out.println(s);
break;
}
}
}
}
OUTPUT
c
It returns the copy of the String by removing whitespaces at both ends.
String s1 = " Code Rovers Duo ";
String s2 = s1.trim();
System.Out.Println(s2);
// Prints "Code Rovers Duo"
package stringmanipulation;
public class ReverseString {
public static void main(String[] args) {
String s = "ABCD";
reverseStr(s);
}
private static void reverseStr(String s) {
StringBuilder builder = new StringBuilder();
for (int i = s.length() - 1; i >= 0; i--) {
builder.append(s.charAt(i) + "");
}
System.out.println(builder.toString());
}
}
OUTPUT
DCBA
Yes, String class is final because of which we can achieve immutability for that class.
Using Integer.parseInt() method. Refer the below example for detailed explanation.
package stringmanipulation;
public class StringToInt {
public static void main(String[] args) {
// Declaringthe String variable
String str = "420";
// Converting String into Integer
int integerVal = Integer.parseInt(str);
System.out.println(str + 200);// 420200, String concatenation
System.out.println(integerVal + 100);// 520, Integer Addition
}
}