Java Language
स्ट्रिंग्स
खोज…
परिचय
स्ट्रिंग्स ( java.lang.String
) आपके प्रोग्राम में संग्रहीत पाठ के टुकड़े हैं। स्ट्रिंग्स जावा में एक आदिम डेटा प्रकार नहीं हैं, हालांकि, वे जावा कार्यक्रमों में बहुत आम हैं।
जावा में, स्ट्रिंग्स अपरिवर्तनीय हैं, जिसका अर्थ है कि उन्हें बदला नहीं जा सकता है। (अपरिवर्तनीयता के अधिक गहन विवरण के लिए यहां क्लिक करें ।)
टिप्पणियों
के बाद से जावा तार कर रहे हैं अपरिवर्तनीय , सभी तरीकों जो एक हेरफेर String
एक नया वापस आ जाएगी String
वस्तु। वे मूल String
को नहीं बदलते हैं। इसमें स्ट्रिंग और प्रतिस्थापन के तरीके शामिल हैं जो C और C ++ प्रोग्रामर लक्ष्य String
ऑब्जेक्ट को म्यूट करने की अपेक्षा करेंगे।
यदि आप दो से अधिक String
ऑब्जेक्ट्स को संकलित करना चाहते हैं, जिनके String
संकलन समय पर निर्धारित नहीं किया जा सकता है, तो String
बजाय एक StringBuilder
उपयोग करें। यह तकनीक नई String
वस्तुओं को बनाने और उन्हें StringBuilder
बनाने की तुलना में अधिक प्रदर्शन करने वाली है क्योंकि String
StringBuilder
परिवर्तनशील है।
StringBuffer
उपयोग String
वस्तुओं को समेटने के लिए भी किया जा सकता है। हालांकि, यह वर्ग कम प्रदर्शन वाला है क्योंकि यह थ्रेड-सुरक्षित होने के लिए डिज़ाइन किया गया है, और प्रत्येक ऑपरेशन से पहले एक म्यूटेक्स प्राप्त करता है। जब से तुम लगभग धागे की सुरक्षा जब तार श्रृंखलाबद्ध की जरूरत कभी नहीं, यह सबसे अच्छा उपयोग करने के लिए है StringBuilder
।
यदि आप एक एकल अभिव्यक्ति के रूप में एक स्ट्रिंग संयोजन व्यक्त कर सकते हैं, तो +
ऑपरेटर का उपयोग करना बेहतर है। Java कंपाइलर +
String.concat(...)
+
String.concat(...)
को संक्रिया के एक कुशल अनुक्रम में String.concat(...)
या StringBuilder
का उपयोग करके परिवर्तित करेगा। StringBuilder
का उपयोग करने की सलाह स्पष्ट रूप से केवल तब लागू होती है जब संघनन में कई भाव शामिल होते हैं।
संवेदनशील सूचनाओं को स्ट्रिंग में संग्रहीत न करें। यदि कोई आपके चलने वाले एप्लिकेशन की मेमोरी डंप प्राप्त करने में सक्षम है, तो वे सभी मौजूदा String
वस्तुओं को खोजने और उनकी सामग्री को पढ़ने में सक्षम होंगे। इसमें String
ऑब्जेक्ट शामिल हैं जो अगम्य हैं और कचरा संग्रह की प्रतीक्षा कर रहे हैं। यदि यह एक चिंता का विषय है, तो आपको संवेदनशील स्ट्रिंग डेटा पोंछने की आवश्यकता होगी जैसे ही आप इसके साथ काम करेंगे। आप String
वस्तुओं के साथ ऐसा नहीं कर सकते क्योंकि वे अपरिवर्तनीय हैं। इसलिए, संवेदनशील चरित्र डेटा रखने के लिए एक char[]
वस्तुओं का उपयोग करने की सलाह दी जाती है, और जब आप कर रहे हों तो उन्हें मिटा दें (उदाहरण के लिए '\000'
अक्षर '\000'
साथ उन्हें ओवरराइट करें)।
सभी String
इंस्टेंसेस को ढेर पर बनाया जाता है, यहां तक कि ऐसे इंस्टेंस जो स्ट्रिंग लिटरल्स के अनुरूप हैं। स्ट्रिंग शाब्दिकों के बारे में विशेष बात यह है कि JVM यह सुनिश्चित करता है कि सभी शाब्दिक शब्द समान हैं (अर्थात एक ही वर्ण के) एक एकल String
ऑब्जेक्ट द्वारा दर्शाए जाते हैं (यह व्यवहार JLS में निर्दिष्ट है)। यह जेवीएम वर्ग लोडरों द्वारा कार्यान्वित किया जाता है। जब एक क्लास लोडर एक कक्षा को लोड करता है, तो यह स्ट्रिंग डेफिनल्स के लिए स्कैन करता है जो कि क्लास डेफिनिशन में उपयोग किए जाते हैं, हर बार जब यह एक को देखता है, तो यह चेक करता है कि क्या इस शाब्दिक के लिए स्ट्रिंग पूल में पहले से ही एक रिकॉर्ड है (एक कुंजी के रूप में शाब्दिक का उपयोग करके) । यदि शाब्दिक के लिए पहले से ही एक प्रविष्टि है, तो उस शाब्दिक के लिए जोड़ी के रूप में संग्रहीत String
उदाहरण का संदर्भ उपयोग किया जाता है। अन्यथा, एक नया String
इंस्टेंस बनाया जाता है और इंस्टेंस का एक संदर्भ स्ट्रिंग पूल में शाब्दिक (एक कुंजी के रूप में प्रयुक्त) के लिए संग्रहीत किया जाता है। (इसके अलावा स्ट्रिंग इंटर्निंग देखें)।
स्ट्रिंग पूल जावा हीप में आयोजित किया जाता है, और सामान्य कचरा संग्रह के अधीन है।
जावा 7 के पहले जावा के रिलीज में, स्ट्रिंग पूल को "पर्मगेन" के रूप में जाने वाले ढेर के एक विशेष हिस्से में आयोजित किया गया था। यह हिस्सा कभी-कभार ही एकत्र होता था।
जावा 7 में, स्ट्रिंग पूल को "पर्मगेन" से हटा दिया गया था।
ध्यान दें कि स्ट्रिंग शाब्दिक रूप से किसी भी विधि से उपयोग करने योग्य हैं जो उनका उपयोग करता है। इसका अर्थ है कि संबंधित String
ऑब्जेक्ट्स को केवल तभी एकत्रित किया जा सकता है यदि कोड स्वयं कचरा एकत्र किया गया हो।
जावा 8 तक, String
ऑब्जेक्ट्स को UTF-16 चार सरणी (प्रति चार्ट 2 बाइट्स) के रूप में लागू किया जाता है। जावा 9 में एक प्रस्ताव है कि स्ट्रिंग को बाइट्स (LATIN-1) या चार्ट (UTF-16) के रूप में एन्कोड किया गया है, यह ध्यान देने के लिए एन्कोडिंग फ्लैग फ़ील्ड के साथ बाइट सरणी के रूप में String
को लागू करने के लिए।
तुलना स्ट्रिंग्स
स्ट्रिंग्स की समानता के लिए तुलना करने के लिए, आपको स्ट्रिंग ऑब्जेक्ट की equals
या equalsIgnoreCase
का उपयोग करना चाहिए।
उदाहरण के लिए, निम्नलिखित स्निपेट यह निर्धारित करेगा कि String
के दो उदाहरण सभी वर्णों पर समान हैं:
String firstString = "Test123";
String secondString = "Test" + 123;
if (firstString.equals(secondString)) {
// Both Strings have the same content.
}
यह उदाहरण उनकी तुलना करेगा, उनके मामले से स्वतंत्र:
String firstString = "Test123";
String secondString = "TEST123";
if (firstString.equalsIgnoreCase(secondString)) {
// Both Strings are equal, ignoring the case of the individual characters.
}
ध्यान दें कि equalsIgnoreCase
आपको एक Locale
निर्दिष्ट नहीं करने देता है। उदाहरण के लिए, यदि आप अंग्रेजी के दो शब्दों "Taki"
और "TAKI"
"Taki"
तुलना करते हैं, तो वे समान हैं; हालाँकि, तुर्की में वे अलग हैं (तुर्की में, लोअरकेस I
ı
)। इस तरह के मामलों के लिए, Locale
साथ लोअरकेस (या अपरकेस) दोनों स्ट्रिंग्स को कनवर्ट करना और फिर equals
साथ तुलना करना समाधान है।
String firstString = "Taki";
String secondString = "TAKI";
System.out.println(firstString.equalsIgnoreCase(secondString)); //prints true
Locale locale = Locale.forLanguageTag("tr-TR");
System.out.println(firstString.toLowerCase(locale).equals(
secondString.toLowerCase(locale))); //prints false
स्ट्रिंग्स की तुलना करने के लिए == ऑपरेटर का उपयोग न करें
जब तक आप यह गारंटी नहीं दे सकते कि सभी तारों को नजरबंद कर दिया गया है (नीचे देखें), आपको स्ट्रिंग्स की तुलना करने के लिए ==
या !=
ऑपरेटरों का उपयोग नहीं करना चाहिए । ये ऑपरेटर वास्तव में संदर्भों का परीक्षण करते हैं, और चूंकि कई String
ऑब्जेक्ट एक ही स्ट्रिंग का प्रतिनिधित्व कर सकते हैं, यह गलत उत्तर देने के लिए उत्तरदायी है।
इसके बजाय, String.equals(Object)
विधि का उपयोग करें, जो स्ट्रिंग की वस्तुओं की उनके मूल्यों के आधार पर तुलना करेगा। विस्तृत विवरण के लिए, तार की तुलना करने के लिए कृपया == का उपयोग करके पिटफॉल देखें।
एक स्विच स्टेटमेंट में स्ट्रिंग्स की तुलना करना
जावा 1.7 के अनुसार, switch
स्टेटमेंट में स्ट्रिंग वेरिएबल की तुलना शाब्दिक से करना संभव है। सुनिश्चित करें कि स्ट्रिंग शून्य नहीं है, अन्यथा यह हमेशा NullPointerException
फेंक देगा। मानों की तुलना String.equals
, अर्थात केस संवेदी के उपयोग से की String.equals
।
String stringToSwitch = "A";
switch (stringToSwitch) {
case "a":
System.out.println("a");
break;
case "A":
System.out.println("A"); //the code goes here
break;
case "B":
System.out.println("B");
break;
default:
break;
}
निरंतर मूल्यों के साथ स्ट्रिंग्स की तुलना करना
एक String
को स्थिर मान से तुलना करते समय, आप यह सुनिश्चित करने के लिए बायीं ओर के equals
मूल्य पर निरंतर मान रख सकते हैं कि आपको NullPointerException
नहीं मिलेगी यदि अन्य स्ट्रिंग null
।
"baz".equals(foo)
जबकि foo.equals("baz")
एक NullPointerException
को फेंक देगा यदि foo
null
, "baz".equals(foo)
false
मूल्यांकन करेगा।
एक अधिक पठनीय विकल्प Objects.equals()
का उपयोग Objects.equals()
, जो दोनों मापदंडों पर एक अशक्त जांच करता है: Objects.equals(foo, "baz")
।
( नोट: यह बहस करने योग्य है कि क्या सामान्य रूप से NullPointerExceptions
से बचना बेहतर है, या उन्हें होने दें और फिर मूल कारण को ठीक करें । यहाँ और यहाँ देखें। निश्चित रूप से, परिहार रणनीति को "सर्वोत्तम अभ्यास" कहना उचित नहीं है।)
स्ट्रिंग के आदेश
String
क्लास String.compareTo
Comparable<String>
साथ Comparable<String>
String.compareTo
मेथड (जैसा कि इस उदाहरण की शुरुआत में वर्णित है)। यह String
ऑब्जेक्ट्स को केस-संवेदी आदेश का प्राकृतिक क्रम बनाता है। String
वर्ग एक Comparator<String>
प्रदान करता है Comparator<String>
निरंतर केस-असंवेदनशील छँटाई के लिए उपयुक्त CASE_INSENSITIVE_ORDER
कहलाता है।
नजरबंद स्ट्रिंग्स के साथ तुलना
जावा भाषा विशिष्टता ( JLS 3.10.6 ) निम्नलिखित बताती है:
"इसके अलावा, एक स्ट्रिंग शाब्दिक हमेशा कक्षा
String
के एक ही उदाहरण को संदर्भित करता है। इसका कारण यह है कि स्ट्रिंग शाब्दिक - या, अधिक सामान्यतः, स्ट्रिंग जो निरंतर अभिव्यक्तियों के मूल्य हैं - को अनूठे उदाहरणों को साझा करने के लिए इंटर्न किया जाता है, विधिString.intern
का उपयोग करकेString.intern
। "
इसका मतलब यह है कि ==
का उपयोग करके दो स्ट्रिंग लीटर के संदर्भों की तुलना करना सुरक्षित है। इसके अलावा, String
ऑब्जेक्ट्स के संदर्भ के लिए भी ऐसा ही है जो String.intern()
विधि का उपयोग करके निर्मित किया गया है।
उदाहरण के लिए:
String strObj = new String("Hello!");
String str = "Hello!";
// The two string references point two strings that are equal
if (strObj.equals(str)) {
System.out.println("The strings are equal");
}
// The two string references do not point to the same object
if (strObj != str) {
System.out.println("The strings are not the same object");
}
// If we intern a string that is equal to a given literal, the result is
// a string that has the same reference as the literal.
String internedStr = strObj.intern();
if (internedStr == str) {
System.out.println("The interned string and the literal are the same object");
}
परदे के पीछे, होना शामिल तंत्र है कि सभी प्रशिक्षु तार है कि अभी भी पहुंचा जा सकता है शामिल है एक हैश तालिका रखता है। जब आप एक String
पर intern()
कॉल करते हैं, तो विधि हैश तालिका में ऑब्जेक्ट दिखता है:
- यदि स्ट्रिंग पाया जाता है, तो उस मान को इंटर्न स्ट्रिंग के रूप में वापस किया जाता है।
- अन्यथा, स्ट्रिंग की एक प्रतिलिपि हैश तालिका में जोड़ी जाती है और उस स्ट्रिंग को इंटर्न स्ट्रिंग के रूप में वापस किया जाता है।
==
का उपयोग करके तारों की तुलना करने की अनुमति देने के लिए इंटर्निंग का उपयोग करना संभव है। हालांकि, ऐसा करने के साथ महत्वपूर्ण समस्याएं हैं; पिटफट देखें - इंटरस्टिंग तार ताकि आप उपयोग कर सकें == विवरण के लिए एक बुरा विचार है। यह ज्यादातर मामलों में अनुशंसित नहीं है।
एक स्ट्रिंग के भीतर पात्रों के मामले को बदलना
String
प्रकार ऊपरी मामले और निचले मामले के बीच तार बदलने के लिए दो तरीके प्रदान करता है:
- ऊपरी चरित्र के सभी वर्णों को परिवर्तित करने के लिए
toUpperCase
- सभी वर्णों को निचले मामले में बदलने के लिए
toLowerCase
करें
ये पद्धतियाँ परिवर्तित स्ट्रिंग को नए String
इंस्टेंस के रूप में String
हैं: मूल String
ऑब्जेक्ट्स को संशोधित नहीं किया जाता है क्योंकि String
जावा में अपरिवर्तनीय है। इसे अपरिपक्वता पर अधिक के लिए देखें: जावा में स्ट्रिंग्स की अपरिवर्तनीयता
String string = "This is a Random String";
String upper = string.toUpperCase();
String lower = string.toLowerCase();
System.out.println(string); // prints "This is a Random String"
System.out.println(lower); // prints "this is a random string"
System.out.println(upper); // prints "THIS IS A RANDOM STRING"
गैर-अक्षर वर्ण, जैसे अंक और विराम चिह्न, इन विधियों से अप्रभावित हैं। ध्यान दें कि ये विधियाँ कुछ शर्तों के तहत कुछ यूनिकोड वर्णों के साथ गलत तरीके से भी व्यवहार कर सकती हैं।
नोट : ये विधियां स्थानीय-संवेदनशील हैं , और अप्रत्याशित परिणाम उत्पन्न कर सकते हैं यदि इनका उपयोग ऐसे तार पर किया जाता है, जिन्हें लोकेल से स्वतंत्र समझा जाता है। उदाहरण भाषा पहचानकर्ता, प्रोटोकॉल कुंजी और HTML
टैग्स हैं।
उदाहरण के लिए, एक तुर्की स्थान में "TITLE".toLowerCase()
" tıtle
" देता है, जहां ı (\u0131)
LATIN SMALL LETTER DOTLESS I चरित्र है। लोकल असंवेदनशील स्ट्रिंग्स के लिए सही परिणाम प्राप्त करने के लिए, Locale.ROOT
को उसी केस toLowerCase(Locale.ROOT)
मेथड (जैसे toLowerCase(Locale.ROOT)
या toUpperCase(Locale.ROOT)
) के पैरामीटर के रूप में पास करें।
हालांकि Locale.ENGLISH
का उपयोग Locale.ENGLISH
अधिकांश मामलों के लिए भी सही है, लेकिन भाषा अपरिवर्तनीय तरीका Locale.ROOT
।
यूनिकोड वर्णों की एक विस्तृत सूची जिसमें विशेष आवरण की आवश्यकता होती है , यूनिकोड कंसोर्टियम वेबसाइट पर पाया जा सकता है।
एक ASCII स्ट्रिंग के भीतर एक विशिष्ट चरित्र का मामला बदलना:
एल्गोरिथ्म के बाद ASCII स्ट्रिंग के विशिष्ट वर्ण के मामले को बदलने के लिए इस्तेमाल किया जा सकता है:
कदम:
- एक स्ट्रिंग घोषित करें।
- स्ट्रिंग इनपुट करें।
- स्ट्रिंग को कैरेक्टर ऐरे में बदलें।
- उस चरित्र को इनपुट करें जिसे खोजा जाना है।
- चरित्र सरणी में वर्ण के लिए खोजें।
- यदि पाया जाता है, तो जांच लें कि चरित्र कम है या अपरकेस।
- यदि अपरकेस, तो चरित्र के ASCII कोड में 32 जोड़ें।
- यदि लोअरकेस, चरित्र के ASCII कोड से 32 घटाएं।
- वर्ण सरणी से मूल वर्ण बदलें।
- वर्ण सरणी को वापस स्ट्रिंग में बदलें।
वोइला, चरित्र का मामला बदल जाता है।
एल्गोरिथ्म के लिए कोड का एक उदाहरण है:
Scanner scanner = new Scanner(System.in);
System.out.println("Enter the String");
String s = scanner.next();
char[] a = s.toCharArray();
System.out.println("Enter the character you are looking for");
System.out.println(s);
String c = scanner.next();
char d = c.charAt(0);
for (int i = 0; i <= s.length(); i++) {
if (a[i] == d) {
if (d >= 'a' && d <= 'z') {
d -= 32;
} else if (d >= 'A' && d <= 'Z') {
d += 32;
}
a[i] = d;
break;
}
}
s = String.valueOf(a);
System.out.println(s);
दूसरे स्ट्रिंग के भीतर एक स्ट्रिंग खोजना
क्या एक विशेष स्ट्रिंग की जांच करने के a
एक स्ट्रिंग में निहित किया जा रहा है b
या नहीं, हम विधि का उपयोग कर सकते हैं String.contains()
निम्न सिंटैक्स के साथ:
b.contains(a); // Return true if a is contained in b, false otherwise
String.contains()
विधि का उपयोग यह सत्यापित करने के लिए किया जा सकता है कि स्ट्रिंग में एक CharSequence
पाया जा सकता है। स्ट्रिंग के लिए विधि दिखता है a
स्ट्रिंग में b
एक केस-संवेदी तरीके से।
String str1 = "Hello World";
String str2 = "Hello";
String str3 = "helLO";
System.out.println(str1.contains(str2)); //prints true
System.out.println(str1.contains(str3)); //prints false
सटीक स्थिति जानने के लिए जहां एक स्ट्रिंग दूसरे स्ट्रिंग के भीतर शुरू होती है, String.indexOf()
उपयोग करें:
String s = "this is a long sentence";
int i = s.indexOf('i'); // the first 'i' in String is at index 2
int j = s.indexOf("long"); // the index of the first occurrence of "long" in s is 10
int k = s.indexOf('z'); // k is -1 because 'z' was not found in String s
int h = s.indexOf("LoNg"); // h is -1 because "LoNg" was not found in String s
String.indexOf()
विधि किसी char
या String
में किसी अन्य String
के पहले अनुक्रमणिका देता है। विधि -1
अगर यह नहीं मिला है।
नोट : String.indexOf()
विधि संवेदनशील है।
मामले की अनदेखी करने वाले खोज का उदाहरण:
String str1 = "Hello World";
String str2 = "wOr";
str1.indexOf(str2); // -1
str1.toLowerCase().contains(str2.toLowerCase()); // true
str1.toLowerCase().indexOf(str2.toLowerCase()); // 6
एक स्ट्रिंग की लंबाई हो रही है
एक String
ऑब्जेक्ट की लंबाई प्राप्त करने के लिए, उस पर length()
विधि को कॉल करें। लंबाई स्ट्रिंग में UTF-16 कोड इकाइयों (वर्ण) की संख्या के बराबर है।
String str = "Hello, World!";
System.out.println(str.length()); // Prints out 13
एक char
एक स्ट्रिंग में UTF-16 के मूल्य है। यूनिकोड कोडपॉइंट्स जिनके मान whose 0x1000 हैं (उदाहरण के लिए, अधिकांश इमोजी) दो चार पदों का उपयोग करते हैं। स्ट्रिंग में यूनिकोड कोडपॉइंट्स की संख्या की गणना करने के लिए, भले ही प्रत्येक codePointCount
यूटीएफ -16 char
मूल्य में फिट हो, आप codePointCount
विधि का उपयोग कर सकते हैं:
int length = str.codePointCount(0, str.length());
आप Java 8 के रूप में, कोडपॉइंट की एक स्ट्रीम का भी उपयोग कर सकते हैं:
int length = str.codePoints().count();
सबस्ट्रिंग
String s = "this is an example";
String a = s.substring(11); // a will hold the string starting at character 11 until the end ("example")
String b = s.substring(5, 10); // b will hold the string starting at character 5 and ending right before character 10 ("is an")
String b = s.substring(5, b.length()-3); // b will hold the string starting at character 5 ending right before b' s lenght is out of 3 ("is an exam")
सबस्ट्रिंग को स्लाइस पर लागू किया जा सकता है और इसके मूल स्ट्रिंग में चरित्र को जोड़ / बदल सकता है। उदाहरण के लिए, आपने एक चीनी तिथि का सामना किया है जिसमें चीनी वर्ण हैं लेकिन आप इसे एक अच्छी तरह से दिनांक स्ट्रिंग के रूप में संग्रहीत करना चाहते हैं।
String datestring = "2015年11月17日"
datestring = datestring.substring(0, 4) + "-" + datestring.substring(5,7) + "-" + datestring.substring(8,10);
//Result will be 2015-11-17
प्रतिस्थापन विधि एक String
का एक टुकड़ा निकालती है। जब एक पैरामीटर प्रदान किया जाता है, तो पैरामीटर प्रारंभ होता है और String
के अंत तक टुकड़ा फैलता है। जब दो पैरामीटर दिए जाते हैं, तो पहला पैरामीटर प्रारंभिक वर्ण होता है और दूसरा पैरामीटर अंत के ठीक बाद वर्ण का सूचकांक होता है (सूचकांक में वर्ण शामिल नहीं है)। जाँच करने का एक आसान तरीका यह है कि दूसरे से पहले पैरामीटर का घटाव स्ट्रिंग की अपेक्षित लंबाई का उत्पादन करे।
JDK <7u6 संस्करणों में substring
विधि एक String
को इंस्टेंटेट करता है जो मूल String
के समान char[]
बैकिंग char[]
साझा करता है और परिणाम शुरू और लंबाई के लिए निर्धारित आंतरिक offset
और count
फ़ील्ड है। इस तरह के साझाकरण से मेमोरी लीक हो सकती है, जिसे कॉपी करने के लिए मजबूर करने के लिए new String(s.substring(...))
को कॉल करके रोका जा सकता है, जिसके बाद char[]
एकत्र किया जा सकता है।
JDK 7u6 से substring
विधि हमेशा संपूर्ण अंतर्निहित char[]
सरणी को कॉपी करती है, जिससे पिछले एक की तुलना में जटिलता रैखिक हो जाती है लेकिन एक ही समय में मेमोरी लीक की अनुपस्थिति की गारंटी देता है।
एक स्ट्रिंग में nth चरित्र प्राप्त करना
String str = "My String";
System.out.println(str.charAt(0)); // "M"
System.out.println(str.charAt(1)); // "y"
System.out.println(str.charAt(2)); // " "
System.out.println(str.charAt(str.length-1)); // Last character "g"
एक स्ट्रिंग में nth वर्ण प्राप्त करने के लिए, बस एक String
पर charAt(n)
कॉल करें, जहाँ n
उस वर्ण का सूचकांक है जिसे आप पुनः प्राप्त करना चाहेंगे
नोट: इंडेक्स n
0
से शुरू हो रहा है, इसलिए पहला तत्व n = 0 पर है।
प्लेटफ़ॉर्म स्वतंत्र नई लाइन विभाजक
चूंकि नई लाइन विभाजक प्लेटफ़ॉर्म से प्लेटफ़ॉर्म (जैसे \n
पर यूनिक्स जैसी प्रणालियों या विंडोज पर \r\n
) में बदलती है, इसलिए इसे एक्सेस करने का प्लेटफ़ॉर्म-स्वतंत्र तरीका होना अक्सर आवश्यक होता है। जावा में इसे एक सिस्टम प्रॉपर्टी से प्राप्त किया जा सकता है:
System.getProperty("line.separator")
क्योंकि नई लाइन सेपरेटर की आमतौर पर आवश्यकता होती है, जावा 7 से एक शॉर्टकट विधि पर ठीक उसी तरह से लौटने वाला परिणाम जैसा कि ऊपर कोड उपलब्ध है:
System.lineSeparator()
नोट : चूंकि यह बहुत संभावना नहीं है कि नई लाइन सेपरेटर प्रोग्राम के निष्पादन के दौरान बदल जाती है, इसलिए इसे हर बार जरूरत पड़ने पर सिस्टम प्रॉपर्टी से इसे पुनर्प्राप्त करने के बजाय एक स्थिर अंतिम चर में स्टोर करना एक अच्छा विचार है।
String.format
का उपयोग करते समय, प्लेटफ़ॉर्म स्वतंत्र नई लाइन विभाजक को आउटपुट करने के लिए \n
या 'r \ n' के बजाय %n
उपयोग करें।
System.out.println(String.format('line 1: %s.%nline 2: %s%n', lines[0],lines[1]));
कस्टम ऑब्जेक्ट्स के लिए toString () विधि जोड़ना
मान लीजिए कि आपने निम्नलिखित Person
वर्ग को परिभाषित किया है:
public class Person {
String name;
int age;
public Person (int age, String name) {
this.age = age;
this.name = name;
}
}
यदि आप एक नए Person
वस्तु को तत्काल करते हैं:
Person person = new Person(25, "John");
और बाद में अपने कोड में आप ऑब्जेक्ट को प्रिंट करने के लिए निम्नलिखित कथन का उपयोग करते हैं:
System.out.println(person.toString());
आपको निम्नलिखित के समान आउटपुट मिलेगा:
Person@7ab89d
यह Object
क्लास, Person
का एक सुपरक्लास में परिभाषित toString()
पद्धति के कार्यान्वयन का परिणाम है। Object.toString()
प्रलेखन में कहा गया है:
क्लास ऑब्जेक्ट के लिए स्ट्रींगिंग विधि एक स्ट्रिंग लौटाती है जिसमें उस क्लास के नाम के साथ ऑब्जेक्ट होता है जो ऑब्जेक्ट एक उदाहरण, ऑन-साइन कैरेक्टर `@ 'और ऑब्जेक्ट के हैश कोड के अहस्ताक्षरित हेक्साडेसिमल प्रतिनिधित्व है। दूसरे शब्दों में, यह विधि एक मान के बराबर स्ट्रिंग लौटाती है:
getClass().getName() + '@' + Integer.toHexString(hashCode())
तो, सार्थक आउटपुट के लिए, आपको toString()
विधि को ओवरराइड करना होगा:
@Override
public String toString() {
return "My name is " + this.name + " and my age is " + this.age;
}
अब उत्पादन होगा:
My name is John and my age is 25
आप भी लिख सकते हैं
System.out.println(person);
वास्तव में, println()
का toString
वस्तु पर toString
विधि से है।
बंटवारे के तार
आप किसी विशेष परिसीमन वर्ण या नियमित अभिव्यक्ति पर एक String
को विभाजित कर सकते हैं, आप निम्न हस्ताक्षर वाले String.split()
विधि का उपयोग कर सकते हैं:
public String[] split(String regex)
ध्यान दें कि परिणामी स्ट्रिंग एरे से परिसीमन वर्ण या नियमित अभिव्यक्ति हटा दी जाती है।
उदाहरण परिसीमन वर्ण का उपयोग करते हुए:
String lineFromCsvFile = "Mickey;Bolton;12345;121216";
String[] dataCells = lineFromCsvFile.split(";");
// Result is dataCells = { "Mickey", "Bolton", "12345", "121216"};
नियमित अभिव्यक्ति का उपयोग करने वाला उदाहरण:
String lineFromInput = "What do you need from me?";
String[] words = lineFromInput.split("\\s+"); // one or more space chars
// Result is words = {"What", "do", "you", "need", "from", "me?"};
तुम भी सीधे एक String
शाब्दिक विभाजित कर सकते हैं:
String[] firstNames = "Mickey, Frank, Alicia, Tom".split(", ");
// Result is firstNames = {"Mickey", "Frank", "Alicia", "Tom"};
चेतावनी : यह मत भूलो कि पैरामीटर को हमेशा एक नियमित अभिव्यक्ति के रूप में माना जाता है।
"aaa.bbb".split("."); // This returns an empty array
पिछले उदाहरण में .
को नियमित अभिव्यक्ति वाइल्डकार्ड के रूप में माना जाता है जो किसी भी चरित्र से मेल खाता है, और चूंकि प्रत्येक चरित्र एक सीमांकक है, परिणाम एक खाली सरणी है।
एक सीमांकक पर आधारित विभाजन, जो एक रेगीक्स मेटा-चरित्र है
Regex में निम्नलिखित वर्णों को विशेष (उर्फ मेटा-वर्ण) माना जाता है
< > - = ! ( ) [ ] { } \ ^ $ | ? * + .
उपरोक्त सीमांकक के आधार पर एक स्ट्रिंग को विभाजित करने के लिए, आपको या तो उन्हें \\
का उपयोग करके बचना होगा या Pattern.quote()
उपयोग करना होगा Pattern.quote()
:
Pattern.quote()
का उपयोग करना:String s = "a|b|c"; String regex = Pattern.quote("|"); String[] arr = s.split(regex);
विशेष पात्रों से बचना:
String s = "a|b|c"; String[] arr = s.split("\\|");
स्प्लिट खाली मानों को हटाता है
split(delimiter)
डिफ़ॉल्ट रूप से परिणाम सरणी से खाली तारों को पीछे हटाता है। इस तंत्र को बंद करने के लिए हमें नकारात्मक मान जैसे निर्धारित सीमा के साथ split(delimiter, limit)
अतिभारित संस्करण का उपयोग करने की आवश्यकता है
String[] split = data.split("\\|", -1);
split(regex)
आंतरिक रूप से split(regex, 0)
परिणाम देता है split(regex, 0)
।
सीमा पैरामीटर पैटर्न लागू होने की संख्या को नियंत्रित करता है और इसलिए परिणामी सरणी की लंबाई को प्रभावित करता है।
यदि सीमा n शून्य से अधिक है, तो पैटर्न को अधिकतम n - 1 बार लागू किया जाएगा, सरणी की लंबाई n से अधिक नहीं होगी, और सरणी की अंतिम प्रविष्टि में अंतिम मिलान किए गए सीमांकक से परे सभी इनपुट होंगे।
यदि एन नकारात्मक है, तो पैटर्न को यथासंभव कई बार लागू किया जाएगा और सरणी में कोई भी लंबाई हो सकती है।
यदि n शून्य है, तो पैटर्न को यथासंभव कई बार लागू किया जाएगा, सरणी में कोई भी लंबाई हो सकती है, और खाली तारों को पीछे छोड़ दिया जाएगा।
एक StringTokenizer
साथ विभाजन
इसके अलावा split()
विधि तार भी एक का उपयोग कर विभाजित किया जा सकता StringTokenizer
।
StringTokenizer
String.split()
तुलना में और भी अधिक प्रतिबंधात्मक है, और उपयोग करने के लिए थोड़ा कठिन भी है। यह अनिवार्य रूप से पात्रों के एक निश्चित सेट (एक String
रूप में दिया गया) द्वारा सीमांकित टोकन बाहर खींचने के लिए डिज़ाइन किया गया है। प्रत्येक चरित्र एक विभाजक के रूप में कार्य करेगा। इस प्रतिबंध के कारण, यह String.split()
रूप में लगभग दोगुना है।
वर्णों का डिफ़ॉल्ट सेट रिक्त स्थान ( \t\n\r\f
) हैं। निम्नलिखित उदाहरण प्रत्येक शब्द को अलग से प्रिंट करेगा।
String str = "the lazy fox jumped over the brown fence";
StringTokenizer tokenizer = new StringTokenizer(str);
while (tokenizer.hasMoreTokens()) {
System.out.println(tokenizer.nextToken());
}
यह प्रिंट होगा:
the
lazy
fox
jumped
over
the
brown
fence
आप अलग करने के लिए विभिन्न वर्ण सेट का उपयोग कर सकते हैं।
String str = "jumped over";
// In this case character `u` and `e` will be used as delimiters
StringTokenizer tokenizer = new StringTokenizer(str, "ue");
while (tokenizer.hasMoreTokens()) {
System.out.println(tokenizer.nextToken());
}
यह प्रिंट होगा:
j
mp
d ov
r
एक परिसीमन के साथ स्ट्रिंग्स में शामिल होना
स्ट्रिंग की एक सरणी स्थिर विधि String.join()
का उपयोग करके शामिल हो सकती है:
String[] elements = { "foo", "bar", "foobar" };
String singleString = String.join(" + ", elements);
System.out.println(singleString); // Prints "foo + bar + foobar"
इसी तरह, Iterable
s के लिए एक अधिभार String.join()
विधि है।
शामिल होने पर एक ठीक-ठाक नियंत्रण रखने के लिए, आप StringJoiner वर्ग का उपयोग कर सकते हैं:
StringJoiner sj = new StringJoiner(", ", "[", "]");
// The last two arguments are optional,
// they define prefix and suffix for the result string
sj.add("foo");
sj.add("bar");
sj.add("foobar");
System.out.println(sj); // Prints "[foo, bar, foobar]"
तार की एक धारा में शामिल होने के लिए, आप शामिल होने वाले कलेक्टर का उपयोग कर सकते हैं:
Stream<String> stringStream = Stream.of("foo", "bar", "foobar");
String joined = stringStream.collect(Collectors.joining(", "));
System.out.println(joined); // Prints "foo, bar, foobar"
यहां उपसर्ग और प्रत्यय को परिभाषित करने का विकल्प है:
Stream<String> stringStream = Stream.of("foo", "bar", "foobar");
String joined = stringStream.collect(Collectors.joining(", ", "{", "}"));
System.out.println(joined); // Prints "{foo, bar, foobar}"
स्ट्रिंग्स उलट
कुछ तरीके हैं जिनसे आप एक स्ट्रिंग को उल्टा कर सकते हैं।
StringBuilder / StringBuffer:
String code = "code"; System.out.println(code); StringBuilder sb = new StringBuilder(code); code = sb.reverse().toString(); System.out.println(code);
चार सरणी:
String code = "code"; System.out.println(code); char[] array = code.toCharArray(); for (int index = 0, mirroredIndex = array.length - 1; index < mirroredIndex; index++, mirroredIndex--) { char temp = array[index]; array[index] = array[mirroredIndex]; array[mirroredIndex] = temp; } // print reversed System.out.println(new String(array));
एक स्ट्रिंग में एक विकल्प या चरित्र की घटनाओं की गिनती
countMatches
से विधि org.apache.commons.lang3.StringUtils आम तौर पर एक-स्ट्रिंग या एक में चरित्र की आवृत्तियां गिनती करने के लिए प्रयोग किया जाता है String
:
import org.apache.commons.lang3.StringUtils;
String text = "One fish, two fish, red fish, blue fish";
// count occurrences of a substring
String stringTarget = "fish";
int stringOccurrences = StringUtils.countMatches(text, stringTarget); // 4
// count occurrences of a char
char charTarget = ',';
int charOccurrences = StringUtils.countMatches(text, charTarget); // 3
अन्यथा मानक जावा एपीआई के साथ भी ऐसा ही है आप नियमित एक्सप्रेशन का उपयोग कर सकते हैं:
import java.util.regex.Matcher;
import java.util.regex.Pattern;
String text = "One fish, two fish, red fish, blue fish";
System.out.println(countStringInString("fish", text)); // prints 4
System.out.println(countStringInString(",", text)); // prints 3
public static int countStringInString(String search, String text) {
Pattern pattern = Pattern.compile(search);
Matcher matcher = pattern.matcher(text);
int stringOccurrences = 0;
while (matcher.find()) {
stringOccurrences++;
}
return stringOccurrences;
}
स्ट्रिंग संघनन और स्ट्रिंगबुइल्डर्स
स्ट्रिंग संधारित्र +
ऑपरेटर का उपयोग करके किया जा सकता है। उदाहरण के लिए:
String s1 = "a";
String s2 = "b";
String s3 = "c";
String s = s1 + s2 + s3; // abc
आम तौर पर एक संकलक कार्यान्वयन हुड के नीचे एक StringBuilder
को शामिल करने वाले तरीकों का उपयोग करके उपरोक्त संयोजन का प्रदर्शन करेगा। संकलित किए जाने पर, कोड नीचे के समान दिखाई देगा:
StringBuilder sb = new StringBuilder("a");
String s = sb.append("b").append("c").toString();
StringBuilder
विभिन्न प्रकारों को लागू करने के लिए कई अतिभारित तरीके हैं, उदाहरण के लिए, एक String
बजाय एक int
को जोड़ने के लिए। उदाहरण के लिए, एक कार्यान्वयन परिवर्तित हो सकता है:
String s1 = "a";
String s2 = "b";
String s = s1 + s2 + 2; // ab2
निम्नलिखित के लिए:
StringBuilder sb = new StringBuilder("a");
String s = sb.append("b").append(2).toString();
उपर्युक्त उदाहरण एक सरल समाकलन प्रक्रिया का वर्णन करते हैं जो प्रभावी रूप से कोड में एक ही स्थान पर किया जाता है। StringBuilder
में StringBuilder
का एक भी उदाहरण शामिल है। कुछ मामलों में, एक संयोजन एक संचयी तरीके से किया जाता है जैसे कि एक लूप में:
String result = "";
for(int i = 0; i < array.length; i++) {
result += extractElement(array[i]);
}
return result;
ऐसे मामलों में, आमतौर पर संकलक अनुकूलन लागू नहीं होता है, और प्रत्येक पुनरावृत्ति एक नया StringBuilder
ऑब्जेक्ट बनाएगा। यह एक StringBuilder
का उपयोग करने के लिए कोड को स्पष्ट रूप से परिवर्तित करके अनुकूलित किया जा सकता है:
StringBuilder result = new StringBuilder();
for(int i = 0; i < array.length; i++) {
result.append(extractElement(array[i]));
}
return result.toString();
एक StringBuilder
को केवल 16 वर्णों के खाली स्थान के साथ आरंभ किया जाएगा। यदि आप पहले से जानते हैं कि आप बड़े तार का निर्माण कर रहे हैं, तो पहले से पर्याप्त आकार के साथ इसे शुरू करना फायदेमंद हो सकता है, ताकि आंतरिक बफर को आकार देने की आवश्यकता न हो:
StringBuilder buf = new StringBuilder(30); // Default is 16 characters
buf.append("0123456789");
buf.append("0123456789"); // Would cause a reallocation of the internal buffer otherwise
String result = buf.toString(); // Produces a 20-chars copy of the string
यदि आप कई तार पैदा कर रहे हैं, तो StringBuilder
एस का पुन: उपयोग करना उचित है:
StringBuilder buf = new StringBuilder(100);
for (int i = 0; i < 100; i++) {
buf.setLength(0); // Empty buffer
buf.append("This is line ").append(i).append('\n');
outputfile.write(buf.toString());
}
एक से अधिक थ्रेड एक ही बफर के लिए लिख रहे हैं (और केवल यदि), का उपयोग StringBuffer , एक है जो synchronized
के संस्करण StringBuilder
। लेकिन क्योंकि आमतौर पर केवल एक ही धागा एक बफर को लिखता है, यह आमतौर पर सिंक्रनाइज़ेशन के बिना StringBuilder
का उपयोग करने के लिए तेज़ होता है।
समवर्ती () विधि का उपयोग करना:
String string1 = "Hello ";
String string2 = "world";
String string3 = string1.concat(string2); // "Hello world"
यह एक नया स्ट्रिंग देता है जो string1 string2 के साथ है इसे अंत में जोड़ा गया है। आप स्ट्रिंग शाब्दिक के साथ कॉनकट () विधि का भी उपयोग कर सकते हैं, जैसे:
"My name is ".concat("Buyya");
स्ट्रिंग्स के कुछ हिस्सों को बदलना
बदलने के दो तरीके: रेगेक्स या सटीक मिलान द्वारा।
ध्यान दें: मूल स्ट्रिंग ऑब्जेक्ट अपरिवर्तित होगा, रिटर्न मान परिवर्तित स्ट्रिंग रखता है।
सटीक मिलान
एकल वर्ण को किसी अन्य एकल वर्ण से बदलें:
String replace(char oldChar, char newChar)
इस स्ट्रिंग में newChar के साथ पुरानेचर की सभी घटनाओं को बदलने के परिणामस्वरूप एक नया स्ट्रिंग लौटाता है।
String s = "popcorn";
System.out.println(s.replace('p','W'));
परिणाम:
WoWcorn
वर्णों के दूसरे अनुक्रम के साथ वर्णों के अनुक्रम को प्रतिस्थापित करें:
String replace(CharSequence target, CharSequence replacement)
इस स्ट्रिंग के प्रत्येक प्रतिस्थापन को प्रतिस्थापित करता है जो निर्दिष्ट शाब्दिक प्रतिस्थापन अनुक्रम के साथ शाब्दिक लक्ष्य अनुक्रम से मेल खाता है।
String s = "metal petal et al.";
System.out.println(s.replace("etal","etallica"));
परिणाम:
metallica petallica et al.
regex
नोट: समूहीकरण का उपयोग करता है $
समूहों संदर्भ के लिए, जैसे चरित्र $1
।
सभी मैचों को बदलें:
String replaceAll(String regex, String replacement)
इस स्ट्रिंग के प्रत्येक प्रतिस्थापन को प्रतिस्थापित करता है जो दिए गए प्रतिस्थापन के साथ दिए गए नियमित अभिव्यक्ति से मेल खाता है।
String s = "spiral metal petal et al.";
System.out.println(s.replaceAll("(\\w*etal)","$1lica"));
परिणाम:
spiral metallica petallica et al.
पहले मैच को ही बदलें:
String replaceFirst(String regex, String replacement)
इस स्ट्रिंग के पहले प्रतिस्थापन को प्रतिस्थापित करता है जो दिए गए प्रतिस्थापन के साथ दिए गए नियमित अभिव्यक्ति से मेल खाता है
String s = "spiral metal petal et al.";
System.out.println(s.replaceAll("(\\w*etal)","$1lica"));
परिणाम:
spiral metallica petal et al.
शुरुआत और एक स्ट्रिंग के अंत से व्हॉट्सएप निकालें
trim()
विधि एक नया स्ट्रिंग लौटाती है जिससे अग्रणी और पीछे वाला व्हाट्सएप हटा दिया जाता है।
String s = new String(" Hello World!! ");
String t = s.trim(); // t = "Hello World!!"
यदि आप एक स्ट्रिंग को trim
करते हैं जिसमें निकालने के लिए कोई व्हाट्सएप नहीं है, तो आपको उसी स्ट्रिंग उदाहरण को वापस कर दिया जाएगा।
ध्यान दें कि trim()
विधि की व्हाट्सएप की अपनी धारणा है , जो कि Character.isWhitespace()
विधि द्वारा उपयोग की जाने वाली धारणा से भिन्न है:
कोड
U+0000
सेU+0020
साथ सभी ASCII नियंत्रण वर्ण कोU+0020
माना जाता है औरtrim()
द्वारा हटा दिया जाता है। इसमेंU+0020 'SPACE'
,U+0009 'CHARACTER TABULATION'
,U+000A 'LINE FEED'
औरU+000D 'CARRIAGE RETURN'
अक्षर शामिल हैं, लेकिनU+0007 'BELL'
के अक्षर भी।U+00A0 'NO-BREAK SPACE'
याU+2003 'EM SPACE'
जैसे यूनिकोडU+00A0 'NO-BREAK SPACE'
trim()
द्वारा मान्यता प्राप्त नहीं हैं।
स्ट्रिंग पूल और ढेर भंडारण
कई जावा ऑब्जेक्ट्स की तरह, सभी String
इंस्टेंस ढेर पर बनाए जाते हैं, यहां तक कि शाब्दिक भी। जब JVM एक String
शाब्दिक पाता है जिसका ढेर में कोई समतुल्य संदर्भ नहीं होता है, तो JVM हीप पर संबंधित String
उदाहरण बनाता है और यह स्ट्रिंग पूल में नए बनाए गए String
उदाहरण के लिए भी संदर्भ संग्रहीत करता है। उसी String
शाब्दिक के किसी भी अन्य संदर्भ को ढेर में पहले से बनाए गए String
उदाहरण से बदल दिया जाता है।
आइए निम्नलिखित उदाहरण देखें:
class Strings
{
public static void main (String[] args)
{
String a = "alpha";
String b = "alpha";
String c = new String("alpha");
//All three strings are equivalent
System.out.println(a.equals(b) && b.equals(c));
//Although only a and b reference the same heap object
System.out.println(a == b);
System.out.println(a != c);
System.out.println(b != c);
}
}
उपरोक्त का आउटपुट है:
true
true
true
true
जब हम एक स्ट्रिंग बनाने के लिए दोहरे उद्धरण चिह्नों का उपयोग करते हैं, तो यह पहली बार स्ट्रिंग पूल में एक ही मान के साथ दिखता है, अगर यह सिर्फ संदर्भ देता है तो यह पूल में एक नया स्ट्रिंग बनाता है और फिर संदर्भ देता है।
हालांकि, नए ऑपरेटर का उपयोग करते हुए, हम String वर्ग को हीप स्पेस में एक नया स्ट्रिंग ऑब्जेक्ट बनाने के लिए मजबूर करते हैं। हम इसे पूल में डालने के लिए इंटर्न () पद्धति का उपयोग कर सकते हैं या समान मूल्य वाले स्ट्रिंग पूल से अन्य स्ट्रिंग ऑब्जेक्ट का उल्लेख कर सकते हैं।
स्ट्रिंग पूल भी हीप पर बना है।
जावा 7 से पहले, String
शाब्दिकों को PermGen
की विधि क्षेत्र में रनटाइम स्थिर पूल में संग्रहीत किया गया था, जिसका एक निश्चित आकार था।
स्ट्रिंग पूल भी PermGen
में रहता था।
JDK 7 में, इंटर्न स्ट्रिंग्स को अब जावा हीप की स्थायी पीढ़ी में आवंटित नहीं किया जाता है, बल्कि उन्हें जावा हीप के मुख्य भाग (युवा और पुरानी पीढ़ी के रूप में जाना जाता है) के साथ-साथ एप्लिकेशन द्वारा बनाई गई अन्य वस्तुओं के साथ आवंटित किया जाता है। । इस परिवर्तन के परिणामस्वरूप मुख्य जावा हीप में अधिक डेटा रहता है, और स्थायी पीढ़ी में कम डेटा, और इस प्रकार ढेर के आकार को समायोजित करने की आवश्यकता हो सकती है। अधिकांश अनुप्रयोग इस परिवर्तन के कारण ढेर उपयोग में केवल अपेक्षाकृत छोटे अंतर देखेंगे, लेकिन कई अनुप्रयोग जो कई कक्षाओं को लोड करते हैं या
String.intern()
विधि का भारी उपयोग करते हैं, वे अधिक महत्वपूर्ण अंतर देखेंगे।
केस असंवेदनशील स्विच
switch
खुद को केस असंवेदनशील होने के लिए toLowerCase()
नहीं किया जा सकता है, लेकिन यदि पूरी तरह से आवश्यक है, तो toLowerCase()
या toUpperCase
का उपयोग करके इनपुट स्ट्रिंग के प्रति असंवेदनशील व्यवहार कर सकता है:
switch (myString.toLowerCase()) {
case "case1" :
...
break;
case "case2" :
...
break;
}
खबरदार
-
Locale
प्रभावित हो सकती है कि बदलते मामले कैसे होते हैं ! - ध्यान रखना चाहिए कि लेबल में कोई अपरकेस अक्षर न हों - जिन्हें कभी निष्पादित नहीं किया जाएगा!