Java String Programs and FAQs
These ten programs come up again and again in fresher interviews, coding tests and college labs. Each uses the tools from this chapter: loops over characters, StringBuilder, split, Character methods, and a couple of maps (collections get their own lessons later; here a map simply counts things). Try each one yourself first, then compare with the solution and read why it works.
The Ten Programs
| # | Program | Input | Output |
|---|---|---|---|
| S1 | Reverse a string | hello | olleh |
| S2 | Palindrome, ignoring case and punctuation | A man, a plan, a canal: Panama | true |
| S3 | Count vowels and consonants | Programming | vowels=3, consonants=8 |
| S4 | Frequency of each character | banana | {a=3, b=1, n=2} |
| S5 | Anagram check | listen, silent | true |
| S6 | First non-repeating character | swiss | w |
| S7 | Reverse the order of words | Java is fun | fun is Java |
| S8 | Remove duplicate characters, keeping order | programming | progamin |
| S9 | Count words with extra spaces | " Java is fun " | 3 |
| S10 | Run-length compression | aaabbc | a3b2c1 |
The Solutions
import java.util.Arrays;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.TreeMap;
public class StringPrograms {
static boolean isPalindrome(String s) {
String clean = s.toLowerCase().replaceAll("[^a-z0-9]", "");
return clean.equals(new StringBuilder(clean).reverse().toString());
}
static String vowelsAndConsonants(String s) {
int vowels = 0, consonants = 0;
for (char ch : s.toLowerCase().toCharArray()) {
if (!Character.isLetter(ch)) continue;
if ("aeiou".indexOf(ch) >= 0) vowels++; else consonants++;
}
return "vowels=" + vowels + ", consonants=" + consonants;
}
static Map<Character, Integer> frequency(String s) {
Map<Character, Integer> freq = new TreeMap<>();
for (char ch : s.toCharArray()) freq.merge(ch, 1, Integer::sum);
return freq;
}
static boolean isAnagram(String a, String b) {
char[] x = a.toLowerCase().toCharArray();
char[] y = b.toLowerCase().toCharArray();
Arrays.sort(x);
Arrays.sort(y);
return Arrays.equals(x, y);
}
static char firstNonRepeating(String s) {
Map<Character, Integer> counts = new LinkedHashMap<>();
for (char ch : s.toCharArray()) counts.merge(ch, 1, Integer::sum);
for (Map.Entry<Character, Integer> e : counts.entrySet()) {
if (e.getValue() == 1) return e.getKey();
}
return '-';
}
static String reverseWords(String s) {
String[] words = s.strip().split("\\s+");
StringBuilder sb = new StringBuilder();
for (int i = words.length - 1; i >= 0; i--) {
sb.append(words[i]);
if (i > 0) sb.append(' ');
}
return sb.toString();
}
static String removeDuplicates(String s) {
StringBuilder sb = new StringBuilder();
for (char ch : s.toCharArray()) {
if (sb.indexOf(String.valueOf(ch)) < 0) sb.append(ch);
}
return sb.toString();
}
static int countWords(String s) {
return s.isBlank() ? 0 : s.strip().split("\\s+").length;
}
static String compress(String s) {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < s.length(); ) {
char ch = s.charAt(i);
int run = 0;
while (i < s.length() && s.charAt(i) == ch) {
i++;
run++;
}
sb.append(ch).append(run);
}
return sb.toString();
}
public static void main(String[] args) {
System.out.println("S1 " + new StringBuilder("hello").reverse());
String panama = "A man, a plan, a canal: Panama";
System.out.println("S2 " + isPalindrome(panama));
System.out.println("S3 " + vowelsAndConsonants("Programming"));
System.out.println("S4 " + frequency("banana"));
System.out.println("S5 " + isAnagram("listen", "silent"));
System.out.println("S6 " + firstNonRepeating("swiss"));
System.out.println("S7 " + reverseWords("Java is fun"));
System.out.println("S8 " + removeDuplicates("programming"));
System.out.println("S9 " + countWords(" Java is fun "));
System.out.println("S10 " + compress("aaabbc"));
}
}S1 olleh
S2 true
S3 vowels=3, consonants=8
S4 {a=3, b=1, n=2}
S5 true
S6 w
S7 fun is Java
S8 progamin
S9 3
S10 a3b2c1Why Each Solution Works
| # | The key idea |
|---|---|
| S1 | StringBuilder.reverse() (see "How to Reverse a String in Java" for the manual way) |
| S2 | First clean the text: lower case, then replaceAll("[^a-z0-9]", "") deletes everything that isn't a letter or digit. Then compare it with its reverse |
| S3 | Skip non-letters with Character.isLetter; "aeiou".indexOf(ch) >= 0 is a neat "is it a vowel?" test |
| S4 | merge(ch, 1, Integer::sum) means "store 1 the first time, otherwise add 1". A TreeMap keeps the letters in order |
| S5 | Two words are anagrams if they contain the same letters: sort both character arrays and compare |
| S6 | Count first, then scan in the original order. LinkedHashMap remembers insertion order, so the first count of 1 is the answer |
| S7 | strip() then split("\\s+") gives clean words; append them from last to first |
| S8 | Keep a character only if the result doesn't contain it yet, which preserves the first occurrence |
| S9 | split("\\s+") treats any run of spaces as one separator; isBlank() handles empty input |
| S10 | Walk through runs of the same character, counting each run before moving on |
How Fast Are They?
Common Mistakes
Comparing characters as strings with ==. char values compare correctly with ==; strings need equals.
Forgetting to normalize case. "Listen" and "silent" are anagrams only after lower-casing.
Splitting on a single space. "a b".split(" ") contains an empty piece; use "\\s+".
Interview Corner
How do you check whether two strings are anagrams?
Normalize both (for example, lower-case them and remove spaces), then either sort their character arrays and compare with Arrays.equals, which takes O(n log n), or count each letter's occurrences in an int[26] array, adding for one string and subtracting for the other, and check that every count is zero, which takes O(n).
How do you find the first non-repeating character?
Count every character's occurrences in one pass, using a LinkedHashMap or an array, then make a second pass in the original order and return the first character whose count is 1. Both passes are linear, so the whole solution is O(n).
Practice
- Easy: Change S3 to also count digits and spaces, and run it on
"Navika joined in 2026". - Harder: Rewrite S5 using an
int[26]count array instead of sorting, and S8 using aboolean[256]"seen" array. Check that the outputs are unchanged.
Key Takeaways
Was this tutorial helpful?