String in Java : A String in Java is a sequence of characters (text).
Example: String name = "Alice";
Internally, Java stores strings as objects of the String class. Strings are Objects (Not primitive Data type).
Eg: String s = "hello";
means String is not a primitive type (like int or char). It is a class in [Link].
_____________________________________________________________________________
String Pool in Java: The String Pool (also called String Intern Pool) is a special memory region inside the Java
Heap(a special part of the Heap memory), not outside it. It is NOT in Stack, It is NOT in PermGen (after Java
8)
where is the String Pool : Inside the Heap, managed by the JVM. It stores string literals and interned strings
Java Memory Overview (after Java 8)
JVM Memory
│
├── Stack (methods, local variables)
│
└── Heap
├── Young Generation
├── Old Generation
└── **String Pool (inside Heap)** ← This is where interned strings go
Interned Strings in Java : Interning means placing a string into the String Pool so that Java can reuse [Link]
is stored in the String Pool, Shared and reused if another string with the same value already exists,
Managed by the JVM to save memory
Example:
String s1 = "hello"; // goes to String Pool
String s2 = "hello"; // reuses the same pool object
Both s1 and s2 point to the same memory location in the pool.
Heap
│
└── String Pool
├── "hello"
├── "world"
└── "java"
Manual Handling of interned String:
String s1 = new String("hello"); // in heap
String s2 = [Link](); // in pool //Do it manually
String s3 = "hello"; // from pool
Strings are immutable Once created, you cannot change a string. Once a String object is created in Java,
you cannot modify its characters, cannot append inside it, and cannot delete from it. Any operation that looks
like it is modifying the string actually creates a new String object.
Example:
String s = "hello";
s = s + " world";
This does not change "hello". Java actually creates a new String object "hello world". Java creates a new
string: "hello world". s now points to this new string. The old string "hello" still exists in memory (String Pool).
String s = "hello";
The literal "hello" is placed in the String Constant Pool (SCP).
s points to that SCP object.
SCP: "hello" <-- s
2. s = s + " world";
" world" is also a literal → stored in the SCP (if not already).
BUT the expression s + " world" does NOT create a String in SCP.
It creates a new String object on the heap, because string concatenation with + at runtime uses
StringBuilder.
Equivalent code:
s = new StringBuilder() .append(s) .append(" world") .toString();
So the result "hello world" is a new heap object.
After this line:
s stops referring to "hello" in the SCP.
s now refers to the new heap object "hello world".
SCP: Heap:
"hello" "hello world" <-- new s
" world"
Does the compiler/JVM get confused?
No. The variable s is simply updated to reference a new object.
Java references behave like this:
A reference variable can point to only one object at a time.
Assigning a new value to it just re-points the reference.
Old objects remain (until garbage collected) if nothing refers to them.
Strings in C, C++, and Java
Strings in C : Strings in C are arrays of characters ending with a null terminator (\0).
Example : char s[] = "Hello";
Key Points
Not a separate data type → just char[].
You must manage memory manually.
Strings are mutable (you can modify characters).
Functions for string operations are in <string.h> (e.g., strlen(), strcpy(), strcmp()).
Limitations
No automatic resizing.
Prone to errors like buffer overflow.
Strings in C++ (std::string) : C++ provides a real string class: std::string, part of the Standard Template
Library (STL). It internally manages dynamic memory.
Example
std::string s = "Hello";
Key Points
Mutable → characters can be modified.
Automatically resizes as needed.
Provides rich built-in operations: append(), substr(), find(), replace(), etc.
Supports operator overloading: ==, +, +=, [ ] indexing.
✔Advantages over C
Safer, easier, and more powerful than C strings.
Strings in Java (String, StringBuilder, StringBuffer) : Java String is an immutable class, meaning its value
cannot change after creation.
Example String s = "Hello";
✔Key Points
Stored in String Pool when written as literals.
Every modification creates a new object.
Java provides:
o String (immutable)
o StringBuilder (mutable, fast, not thread-safe)
o StringBuffer (mutable, thread-safe)
String Pool
Used to store reusable string literals for memory efficiency.
C Program (Using <string.h> functions)
#include <stdio.h>
#include <string.h>
#include <ctype.h>
int main() {
char s1[50] = "Hello"; char s2[50] = "World"; char copy[50];
printf("Length of s1: %lu\n", strlen(s1)); // Length
strcpy(copy, s1); // Copy
printf("Copy of s1: %s\n", copy);
strcat(s1, " ");// Concatenate
strcat(s1, s2);
printf("Concatenated string: %s\n", s1);
printf("Compare s1 & s2: %d\n", strcmp(s1, s2)); // Compare
if (strstr(s1, "World"))// Substring search
printf("\"World\" found in s1\n");
for (int i = 0; s1[i] != '\0'; i++)// Uppercase
s1[i] = toupper(s1[i]);
printf("Uppercase: %s\n", s1);
return 0;
}
Output:
Length of s1: 5
Copy of s1: Hello
Concatenated string: Hello World
Compare s1 & s2: 15
"World" found in s1
Uppercase: HELLO WORLD
Explanation of key parts of the output:
1. Length of s1: 5
"Hello" has 5 characters.
2. Copy of s1: Hello
strcpy(copy, s1); copies "Hello" into copy.
3. Concatenated string: Hello World
After:
4. strcat(s1, " ");
5. strcat(s1, s2);
s1 becomes "Hello World".
6. Compare s1 & s2: 15
strcmp("Hello World", "World") returns a positive number
(because 'H' (72) - 'W' (87) = -15 initially,
but "Hello World" and "World" differ earlier in ASCII).
Compilers may show 15 or a similar positive value.
7. "World" found in s1
strstr() successfully finds "World" in "Hello World".
8. Uppercase: HELLO WORLD
Loop converts each character using toupper().
C++ Program (Using std::string functions)
#include <iostream>
#include <string>
#include <algorithm>
using namespace std;
int main() {
string s1 = "Hello"; string s2 = "World";
cout << "Length of s1: " << [Link]() << endl; // Length
string copy = s1;
cout << "Copy of s1: " << copy << std::endl; // Copy
s1 += " " + s2; // Concatenate
cout << "Concatenated string: " << s1 << std::endl;
cout << "Compare s1 & s2: " << [Link](s2) << std::endl; // Compare
// npos is a special constant in C++ used with std::string to indicate “not found.”
if ([Link]("World") != string::npos) // Substring search
cout << "\"World\" found in s1\n";
// Uppercase
transform([Link](), [Link](), [Link](), ::toupper);
cout << "Uppercase: " << s1 << endl;
// Substring extraction
std::cout << "Substring (0,5): " << [Link](0, 5) << std::endl;
return 0;
}
Output
Length of s1: 5
Copy of s1: Hello
Concatenated string: Hello World
Compare s1 & s2: 6
"World" found in s1
Uppercase: HELLO WORLD
Substring (0,5): HELLO
Syntax of int compare(const std::string& str) const;
Returns:
0 → if the two strings are equal
> 0 → if *this (s1) is lexicographically greater than str (s2)
< 0 → if *this (s1) is lexicographically smaller than str (s2)
s1 = "Hello World";
s2 = "World";
Compare first characters: 'H' (72) vs 'W' (87)
'H' < 'W' → result is negative?
Explanation:
Explanation of key parts
1. Length of s1: 5
o "Hello" has 5 characters.
2. Copy of s1: Hello
o std::string copy = s1; simply copies the string.
3. Concatenated string: Hello World
o s1 += " " + s2; joins "Hello" + " " + "World" → "Hello World".
4. Compare s1 & s2: 6
o [Link](s2) returns a positive number because "Hello World" > "World" lexicographically.
o The exact number depends on the difference of first non-matching characters in ASCII.
5. "World" found in s1
o [Link]("World") returns an index (6 here), not npos, so the condition is true.
6. Uppercase: HELLO WORLD
o std::transform() with ::toupper converts all letters to uppercase.
7. Substring (0,5): HELLO
o [Link](0, 5) extracts the first 5 characters.
Java Program (Using String functions)
public class Main
{
public static void main(String[] args)
{
String s1 = "Hello"; String s2 = "World";
[Link]("Length of s1: " + [Link]());// Length
String copy = s1; // Copy
[Link]("Copy of s1: " + copy);
String s3 = [Link](" ").concat(s2); // Concatenation
[Link]("Concatenated string: " + s3);
[Link]("Compare s1 & s2: " + [Link](s2)); // Compare
// Substring search
if ([Link]("World")) [Link]("\"World\" found in s3");
// Uppercase & Lowercase
[Link]("Uppercase: " + [Link]());
[Link]("Lowercase: " + [Link]());
// Substring extraction
[Link]("Substring (0,5): " + [Link](0, 5));
// Character search
[Link]("Index of 'W': " + [Link]('W'));
}
}
Output:
Length of s1: 5
Copy of s1: Hello
Concatenated string: Hello World
Compare s1 & s2: -15
"World" found in s3
Uppercase: HELLO WORLD
Lowercase: hello world
Substring (0,5): Hello
Index of 'W': 6
Explanation:
Explanation of each line
1. Length of s1: 5
o "Hello" has 5 characters.
2. Copy of s1: Hello
o String copy = s1; just references the same string (strings are immutable).
3. Concatenated string: Hello World
o [Link](" ").concat(s2) joins the two strings with a space.
4. Compare s1 & s2: -15
o [Link](s2) compares lexicographically.
o 'H' (72) - 'W' (87) = -15.
o Negative means s1 comes before s2.
5. "World" found in s3
o [Link]("World") checks for substring presence.
6. Uppercase: HELLO WORLD
o [Link]() converts all letters to uppercase.
7. Lowercase: hello world
o [Link]() converts all letters to lowercase.
8. Substring (0,5): Hello
o [Link](0,5) extracts the first 5 characters.
9. Index of 'W': 6
o 'W' is at position 6 in "Hello World" (0-based indexing).
Creating Strings
1. Using string literal (preferred)
String s1 = "Hello"; // goes to Pool
2. Using the new keyword
String s2 = new String("Hello"); // goes to Heap, not Pool
This always creates a new object.