2012-03-03 17 views
6

जावा भाषा विनिर्देश बताता है कि तारों के अंदर से बचने के लिए "सामान्य" सी \n और \t हैं, लेकिन वे \0 से \377 से ऑक्टल एस्केप भी निर्दिष्ट करते हैं। विशेष रूप से, JLS राज्यों:जावा ऑक्टल क्यों बचता है केवल 255 तक जाता है?

OctalEscape: 
    \ OctalDigit 
    \ OctalDigit OctalDigit 
    \ ZeroToThree OctalDigit OctalDigit 

OctalDigit: one of 
    0 1 2 3 4 5 6 7 

ZeroToThree: one of 
    0 1 2 3 

जिसका अर्थ है कि \4715 की तरह कुछ, गैर-कानूनी है के बावजूद यह एक जावा चरित्र की सीमा के भीतर किया जा रहा है (के बाद से जावा पात्रों बाइट्स नहीं हैं)।

जावा के मनमाने ढंग से प्रतिबंध क्यों है? 255 से परे वर्णों के लिए ऑक्टल कोड निर्दिष्ट करने का आपका अर्थ कैसा है?

+1

255 मूल ASCII सीमा है यदि मुझे गलत नहीं है, तो आपके पास प्रत्येक आधार ASCII चरित्र के लिए एक है। क्या आप उससे ज्यादा खुश नहीं होना चाहिए? कारण, कहते हैं कि \ 4715 आप पर निर्भर नहीं जा सकते बस है, क्योंकि यह 255 से अधिक मानक ASCII सीमा = डी (मैं, समझा पर बुरा कर रहा हूँ उत्तर देने को देखें) –

+1

@Shingetsu है जो है: ASCII सीमा 127, नहीं 255 है । _Bytes_, 255 तक ही सीमित हैं, जब तक आप जावा बाइट्स हैं जिसके बारे में बात कर रहे हैं, कुछ विचित्र कारण के लिए, पर हस्ताक्षर किए :-) लेकिन जावा पात्रों बाइट्स नहीं हैं। – paxdiablo

+0

[भी देखें] (http://stackoverflow.com/questions/3537706/howto-unescape-a-java-string-literal-in-java/4298836) –

उत्तर

9

के लिए Convert.ToInt32(integer, 8) का उपयोग यह शायद के लिए है पूरी तरह से ऐतिहासिक कारणों से जावा ओक्टल एस्केप दृश्यों का समर्थन करता है। ये बचने के दृश्य सी (या शायद सी के पूर्ववर्ती बी और बीसीपीएल में) में पैदा हुए थे, उन दिनों में जब पीडीपी -7 जैसे कंप्यूटर ने पृथ्वी पर शासन किया था, और अधिक प्रोग्रामिंग असेंबली में या सीधे मशीन कोड में की गई थी, और ऑक्टल पसंदीदा नंबर था निर्देश कोड लिखने के लिए आधार, और कोई यूनिकोड नहीं था, बस ASCII, इसलिए पूरे चरित्र सेट का प्रतिनिधित्व करने के लिए तीन ऑक्टल अंक पर्याप्त थे।

जब तक यूनिकोड और जावा के साथ आया, तो ऑक्टल के पास हेक्साडेसिमल को पसंदीदा संख्या आधार के रूप में बहुत अधिक दिया गया था जब दशमलव केवल ऐसा नहीं करेगा। तो जावा में \u एस्केप अनुक्रम है जो हेक्साडेसिमल अंक लेता है। ऑक्टल एस्केप अनुक्रम शायद सी प्रोग्रामर को आरामदायक बनाने के लिए समर्थित था, और जावा प्रोग्राम्स में सी प्रोग्रामों से कॉपी 'एन' स्टेप स्ट्रिंग स्थिरांक को कॉपी करना आसान बनाता था।

ऐतिहासिक सामान्य ज्ञान के लिए ये लिंक देखें:

http://en.wikipedia.org/wiki/Octal#In_computers
http://en.wikipedia.org/wiki/PDP-11_architecture#Memory_management

+1

+1 यह भी ध्यान दें कि निर्देश कोड लिखने के अलावा भी, जब आप काम कर रहे हैं (उदाहरण के लिए) 36-बिट शब्दों और 9-बिट वर्णों के साथ एक आर्किटेक्चर पर कार्य करता है - 12 ऑक्टल अंक बिल्कुल एक मशीन प्रदर्शित करता है शब्द, प्रत्येक चरित्र के लिए 3 अंक के साथ। यदि आप 9 हेक्स अंकों वाले उसी 36-बिट शब्द का प्रतिनिधित्व करते हैं, तो आप आसानी से अलग-अलग वर्णों के मूल्य को नहीं बता सकते हैं। –

+0

जैसा कि नीचे दिया गया मेरा उत्तर बताता है, \ uXXXX और ऑक्टल एस्केप अनुक्रमों को बहुत अलग चरणों में पार्स किया जाता है। एक \ uXXXX भागने अनुक्रम सी के octal भागने अनुक्रम का एक विस्तारित संस्करण नहीं है। बस एक स्ट्रिंग में \ u000A डालें, और आपका प्रोग्राम संकलन बंद कर देगा। – Sven

1

मैं नियमों को समझने कर सकते हैं (कृपया मुझे सही कर अगर मैं गलत हूँ):

\ OctalDigit 
Examples: 
    \0, \1, \2, \3, \4, \5, \6, \7 

\ OctalDigit OctalDigit 
Examples: 
    \00, \07, \17, \27, \37, \47, \57, \67, \77 

\ ZeroToThree OctalDigit OctalDigit 
Examples: 
    \000, \177, \277, \367,\377 

\t, \n, \\ OctalEscape नियमों के तहत गिर नहीं है; वे अलग-अलग बचने के चरित्र नियमों के तहत होना चाहिए।

दशमलव 255 377 (वैज्ञानिक मोड में विंडोज कैलक्यूलेटर का उपयोग पुष्टि करने के लिए)

इसलिए तीन अंकों ऑक्टल मूल्य की \000 (0) \377 को (255)

रेंज में पड़ता है अष्टाधारी के बराबर है इसलिए, \4715 वैध ऑक्टल मान नहीं है क्योंकि यह तीन-ऑक्टल-अंकों के नियम से अधिक है। यदि आप दशमलव मान 4715 के साथ कोड पॉइंट वर्ण का उपयोग करना चाहते हैं, तो यूटीएफ -16 वर्ण \u126B (दशमलव फॉर्म में 4715) का प्रतिनिधित्व करने के लिए यूनिकोड एस्केप प्रतीक \u का उपयोग करें क्योंकि प्रत्येक जावा char यूनिकोड यूटीएफ -16 में है।

http://docs.oracle.com/javase/1.5.0/docs/api/java/lang/Character.html से

:

The char data type (and therefore the value that a Character object encapsulates) are based on the original Unicode specification, which defined characters as fixed-width 16-bit entities. The Unicode standard has since been changed to allow for characters whose representation requires more than 16 bits. The range of legal code points is now U+0000 to U+10FFFF, known as Unicode scalar value. (Refer to the definition of the U+n notation in the Unicode standard.)

The set of characters from U+0000 to U+FFFF is sometimes referred to as the Basic Multilingual Plane (BMP). Characters whose code points are greater than U+FFFF are called supplementary characters. The Java 2 platform uses the UTF-16 representation in char arrays and in the String and StringBuffer classes. In this representation, supplementary characters are represented as a pair of char values, the first from the high-surrogates range, (\uD800-\uDBFF), the second from the low-surrogates range (\uDC00-\uDFFF).

संपादित:

कोई भी चीज जो 8 बिट सीमा (से बड़ा एक बाइट) के वैध अष्टाधारी मूल्य से परे भाषा-विशिष्ट है। कुछ प्रोग्रामिंग भाषाएं यूनिकोड कार्यान्वयन से मेल खाती हैं; कुछ नहीं हो सकते हैं (इसे एक बाइट तक सीमित करें)। जावा निश्चित रूप से इसे अनुमति नहीं देता है भले ही इसमें यूनिकोड समर्थन है।

कुछ प्रोग्रामिंग भाषाओं (विक्रेता पर निर्भर है) एक-बाइट अष्टाधारी शाब्दिक है कि सीमा:

  1. जावा (सभी विक्रेताओं): - एक अष्टाधारी पूर्णांक लगातार कि 0 या में एकल अंक के साथ शुरू होता बेस -8 (0377 तक); \ 0 से \ 7, \ 00 से \ 77, \ 000 से \ 377 (ऑक्टल स्ट्रिंग शाब्दिक प्रारूप में)
  2. सी/सी ++ (माइक्रोसॉफ्ट) - एक ऑक्टल पूर्णांक निरंतर जो 0 (0377 तक) से शुरू होता है; ऑक्टल स्ट्रिंग शाब्दिक प्रारूप \nnn
  3. रूबी - एक ऑक्टल पूर्णांक निरंतर जो 0 से शुरू होता है (0377 तक); अष्टाधारी स्ट्रिंग शाब्दिक प्रारूप \nnn

कुछ प्रोग्रामिंग भाषाओं (विक्रेता पर निर्भर है) कि बड़े से भी एक-बाइट अष्टाधारी शाब्दिक समर्थन करते हैं:

  1. पर्ल - एक अष्टाधारी पूर्णांक लगातार कि 0 के साथ शुरू होता ; अष्टाधारी स्ट्रिंग शाब्दिक प्रारूप \nnnhttp://search.cpan.org/~jesse/perl-5.12.1/pod/perlrebackslash.pod#Octal_escapes

कुछ प्रोग्रामिंग भाषाओं अष्टाधारी शाब्दिक का समर्थन नहीं करते देखें:

  1. सी # - आधार-8 How can we convert binary number into its octal number using c#?
+0

हाँ, मैं सीमा _know_।मेरा सवाल यह नहीं है कि सीमाएं क्या हैं, बल्कि _why_ उन सीमाएं बिल्कुल हैं, यह देखते हुए कि जावा वर्ण 0-255 तक सीमित नहीं हैं। मैं सवाल स्पष्ट कर दूंगा। – paxdiablo

+0

बेशक, जावा 'स्ट्रिंग' और' char' के लिए यूनिकोड 16-बिट चौड़ा उपयोग कर रहा है। लेकिन अब, आप भागने '\' प्रतीक का उपयोग कर रहे हैं और आप इसे ऑक्टल वैल्यू का प्रतिनिधित्व करने के लिए उपयोग करते हैं जो जावा ऑक्टल से बचने के प्रारूप में या \257' दशमलव मान में केवल \ 377' तक की अनुमति देता है। जावा ऑक्टल एस्केप प्रारूप '\ 4715' वैध ऑक्टल एस्केप प्रारूप नहीं है क्योंकि यह जेएलएस में ऑक्टलएस्केप नियमों के अनुसार तीन अंकों से अधिक है। – ecle

+0

यदि आप यूनिकोड यूटीएफ -16 स्ट्रिंग/चार के तहत 255 से अधिक कोड पॉइंट्स तक पहुंच बनाना चाहते हैं, तो यूनिकोड प्रतीक '\ u' का उपयोग करें। तो, कोड बिंदु 4715 (?) के लिए '\ u4715' (सही रूप है, मुझे लगता है कि यह दशमलव 4715 के लिए' \ u126B' होना चाहिए) – ecle

0

\ 0- \ 377 अष्टाधारी पलायन भी सी से लिए गए हैं, और प्रतिबंध एक भाषा में अर्थ भी पर्याप्त मात्रा में बनाता है सी की तरह जहां अक्षर == बाइट्स (कम से कम hcharcyon दिनों में wchar_t से पहले)।

1

प्रश्न "वास्तविक" प्रश्न का असली जवाब हमें जावा भाषा डिजाइनरों से पूछने की आवश्यकता होगी। हम ऐसा करने की स्थिति में नहीं हैं, और मुझे संदेह है कि वे जवाब देने की स्थिति में भी होंगे। (क्या आप को 20 साल पहले विस्तृत तकनीकी चर्चाओं को याद कर सकते हैं?

  • अष्टाधारी पलायन, C/C++, जिसमें वे भी 8 बिट तक ही सीमित हैं से उधार लिया गया
  • अष्टाधारी पुराने जमाने है:)

    हालांकि, इस "सीमा" के लिए एक प्रशंसनीय विवरण है कि है , और आईटी लोग आम तौर पर पसंद करते हैं और हेक्साडेसिमल के साथ अधिक आरामदायक होते हैं, और

  • जावा यूनिकोड को सीधे स्रोत स्रोत में एम्बेड करके या \u यूनिकोड से बचकर ... स्ट्रिंग और चरित्र तक सीमित नहीं है शाब्दिक।

और ईमानदारी से, मैं कभी किसी को भी (अलग से) सुना है तर्क है कि अष्टाधारी शाब्दिक अब होना चाहिए जावा में 8 बिट से।


संयोग से, जब मैं वर्ण सेट कंप्यूटिंग में शुरू हार्डवेयर विशिष्ट होने की प्रवृत्ति है, और अक्सर कम से कम 8 बिट थे। मेरे स्नातक coursework में, और स्नातक होने के बाद मेरा पहला काम, मैंने सीडीसी 6000 सीरीज़ मशीनों का इस्तेमाल किया जिसमें 60 बिट शब्द और 6 बिट चरित्र सेट - "डिस्प्ले कोड" था, मुझे लगता है कि हमने इसे बुलाया था। इस संदर्भ में ऑक्टल बहुत अच्छी तरह से काम करता है। लेकिन चूंकि उद्योग 8/16/32/64 बिट आर्किटेक्चर के (लगभग) सार्वभौमिक गोद लेने की ओर बढ़ गया, लोगों ने तेजी से ऑक्टल के बजाय हेक्साडेसिमल का उपयोग किया।

0

मुझे कोई कारण नहीं पता कि ऑक्टल से बचने के लिए यूनिकोड कोडपॉइंट्स 0 से 255 तक सीमित क्यों हैं। यह ऐतिहासिक कारणों से हो सकता है। सवाल मूल रूप से अनुत्तरित रहेगा क्योंकि जावा के डिजाइन के दौरान ऑक्टल एस्केप की सीमा को बढ़ाने के लिए कोई तकनीकी कारण नहीं था।

हालांकि यह ध्यान दिया जाना चाहिए, वहाँ यूनिकोड पलायन और अष्टाधारी पलायन के बीच एक नहीं तो स्पष्ट अंतर है कि। Octal escapes केवल स्ट्रिंग्स के हिस्से के रूप में संसाधित होते हैं जबकि यूनिकोड-एस्केप फ़ाइल में कहीं भी हो सकते हैं, उदाहरण के लिए कक्षा के नाम के हिस्से के रूप में। यह भी ध्यान रखें, कि निम्न उदाहरण भी संकलन नहीं होगा:

String a = "\u000A"; 

कारण है, कि \ u000a (मूल रूप से जब फ़ाइल लोड) एक बहुत ही प्रारंभिक चरण में एक नई पंक्ति के लिए विस्तार किया गया है।

String a = "\012"; 

\ 012 के बाद संकलक कोड पार्स है का विस्तार होता है: निम्न कोड एक त्रुटि उत्पन्न नहीं करता है। यह \ n, \ r, \ t, आदि जैसे अन्य भागने के लिए भी है

तो निष्कर्ष में: यूनिकोड से बचने के लिए ऑक्टल से बचने के लिए प्रतिस्थापन नहीं है। वे एक पूरी तरह से अलग अवधारणा हैं। विशेष रूप से, किसी भी समस्या से बचने के लिए (ऊपर \ u000A के साथ), किसी को कोडपॉइंट्स 0 से 255 के लिए ऑक्टल से बचने का उपयोग करना चाहिए और यूनिकोड 255 से ऊपर कोडपॉइंट्स के लिए निकलता है।

संबंधित मुद्दे