การหาตัวอักษรซ้ำ (Duplicate Characters) ในสตริง Java
หาตัวอักษรที่ปรากฏมากกว่า 1 ครั้งในสตริง วิธีง่ายคือใช้ Nested Loops เปรียบเทียบตัวอักษรทุกคู่
อัลกอริทึม (Brute Force O(n²))
- แปลงสตริงเป็นอาร์เรย์ char:
toCharArray() - ลูปภายนอก i: 0 ถึง n-1
- ลูปภายใน j: i+1 ถึง n-1
- ถ้า
char[i] == char[j]→ พบตัวซ้ำ พิมพ์และ break ลูปใน
ตัวอย่างที่ 1: ใน main โดยตรง
public class Demo {
public static void main(String[] args) {
String inputString = "Java Programming";
System.out.println("สตริงต้นฉบับ: " + inputString);
char[] charArray = inputString.toCharArray();
System.out.print("ตัวอักษรซ้ำ: ");
for (int i = 0; i < inputString.length(); i++) {
for (int j = i + 1; j < inputString.length(); j++) {
if (charArray[i] == charArray[j]) {
System.out.print(charArray[j] + " ");
break; // หยุดลูปในเมื่อเจอคู่แรก
}
}
}
}
}
ผลลัพธ์
สตริงต้นฉบับ: Java Programming
ตัวอักษรซ้ำ: a a r g m
ตัวอย่างที่ 2: แบบ OOP
public class Demo {
static void findDuplicates(String input) {
char[] chars = input.toCharArray();
System.out.print("ตัวอักษรซ้ำ: ");
for (int i = 0; i < input.length(); i++) {
for (int j = i + 1; j < input.length(); j++) {
if (chars[i] == chars[j]) {
System.out.print(chars[j] + " ");
break;
}
}
}
System.out.println();
}
public static void main(String[] args) {
findDuplicates("Java Programming");
findDuplicates("Hello World");
}
}
วิธีที่มีประสิทธิภาพมากกว่า: ใช้ HashSet (O(n))
import java.util.*;
public class EfficientDuplicateFinder {
static void findDuplicatesWithSet(String input) {
Set seen = new HashSet<>();
Set duplicates = new LinkedHashSet<>(); // รักษาลำดับ
for (char c : input.toCharArray()) {
if (!seen.add(c)) { // add() คืนค่า false ถ้ามีอยู่แล้ว
duplicates.add(c);
}
}
System.out.println("ตัวอักษรซ้ำ (ไม่ซ้ำกัน): " + duplicates);
}
// นับจำนวนครั้งที่ซ้ำ
static void countDuplicates(String input) {
Map countMap = new HashMap<>();
for (char c : input.toCharArray()) {
countMap.put(c, countMap.getOrDefault(c, 0) + 1);
}
System.out.println("สถิติตัวอักษร:");
countMap.entrySet().stream()
.filter(e -> e.getValue() > 1)
.forEach(e -> System.out.println("'" + e.getKey() + "': " + e.getValue() + " ครั้ง"));
}
public static void main(String[] args) {
String str = "Java Programming";
findDuplicatesWithSet(str);
countDuplicates(str);
}
}
ผลลัพธ์วิธีที่ดีกว่า
ตัวอักษรซ้ำ (ไม่ซ้ำกัน): [a, r, g, m]
สถิติตัวอักษร:
'a': 2 ครั้ง
'r': 2 ครั้ง
'g': 2 ครั้ง
'm': 2 ครั้ง
การเปรียบเทียบวิธีการ
| วิธี | Time Complexity | Space Complexity | ข้อดี |
|---|---|---|---|
| Nested Loops | O(n²) | O(1) | ไม่ต้องใช้พื้นที่เพิ่ม, เข้าใจง่าย |
| HashSet | O(n) | O(n) | เร็วมากสำหรับสตริงยาว |
| HashMap (Count) | O(n) | O(n) | ได้จำนวนครั้งที่ซ้ำด้วย |
| Sort + Scan | O(n log n) | O(1) หรือ O(n) | ไม่ต้องใช้ Hash, เรียงลำดับได้ |
ข้อควรระวัง
- ตัวอย่างเดิมพิมพ์ตัวซ้ำซ้อน (a แสดง 2 ครั้ง) ใช้ Set เพื่อไม่ให้ซ้ำ
- Case-sensitive: 'A' และ 'a' ต่างกัน → ใช้
toLowerCase()ก่อนถ้าต้องการไม่สนใจ case - Space และ punctuation ก็ถูกนับรวม