java - ास्की कोड




कुछ यूनिकोड वर्णों के साथ टिप्पणियों में जावा कोड को क्यों निष्पादित किया जाता है? (6)

केवल वे लोग ही जवाब दे सकते हैं कि यूनिकोड के पलायन को क्यों लागू किया गया क्योंकि वे ऐसे लोग थे जिन्होंने विनिर्देश लिखा था।

इसका एक प्रशंसनीय कारण यह है कि पूरे बीएमपी को जावा स्रोत कोड के संभावित पात्रों के रूप में अनुमति देने की इच्छा थी। हालांकि यह एक समस्या प्रस्तुत करता है:

  • आप किसी भी BMP वर्ण का उपयोग करने में सक्षम होना चाहते हैं।
  • आप किसी भी BMP charater को आसान तरीके से इनपुट करने में सक्षम होना चाहते हैं। ऐसा करने का एक तरीका है यूनिकोड बच जाता है।
  • आप मनुष्यों के पढ़ने और लिखने के लिए शाब्दिक विनिर्देशन को आसान रखना चाहते हैं, और यथोचित रूप से लागू करना आसान है।

यह अविश्वसनीय रूप से मुश्किल है जब यूनिकोड बच जाता है तो मैदान में प्रवेश करता है: यह नए लेसर नियमों का एक पूरा भार बनाता है।

इसका आसान तरीका यह है कि दो चरणों में लेक्सिंग करें: पहले खोज करें और सभी यूनिकोड को उस वर्ण के साथ भाग दें, जो इसके द्वारा निरूपित होता है और फिर परिणामी दस्तावेज़ को पार्स करता है जैसे कि यूनिकोड बचता नहीं है।

इसका उल्टा यह है कि यह निर्दिष्ट करना आसान है, इसलिए यह विनिर्देशन को सरल बनाता है, और इसे लागू करना आसान है।

नकारात्मक पक्ष यह है, ठीक है, आपका उदाहरण।

निम्न कोड आउटपुट "हैलो वर्ल्ड!" (नहीं वास्तव में, यह कोशिश)।

public static void main(String... args) {

   // The comment below is not a typo.
   // \u000d System.out.println("Hello World!");
}

इसका कारण यह है कि जावा कंपाइलर एक नई लाइन के रूप में यूनिकोड वर्ण \u000d को पार्स करता है और इसके लिए रूपांतरित हो जाता है:

public static void main(String... args) {

   // The comment below is not a typo.
   //
   System.out.println("Hello World!");
}

इस प्रकार एक टिप्पणी के परिणामस्वरूप "निष्पादित" किया गया।

चूंकि यह दुर्भावनापूर्ण कोड "छिपाने" के लिए इस्तेमाल किया जा सकता है या जो भी एक दुष्ट प्रोग्रामर गर्भ धारण कर सकता है, उसे टिप्पणियों में क्यों अनुमति दी जाती है ?

जावा विनिर्देश द्वारा इसकी अनुमति क्यों है?


चूंकि यह अभी तक संबोधित नहीं किया गया है, यहां एक स्पष्टीकरण, यूनिकोड का अनुवाद किसी अन्य स्रोत कोड प्रसंस्करण से पहले क्यों होता है:

इसके पीछे यह विचार था कि यह विभिन्न चरित्र एन्कोडिंग के बीच जावा स्रोत कोड के दोषरहित अनुवाद की अनुमति देता है। आज, व्यापक यूनिकोड समर्थन है, और यह एक समस्या की तरह नहीं दिखता है, लेकिन फिर एक पश्चिमी देश के एक डेवलपर के लिए अपने एशियाई सहयोगी से कुछ स्रोत कोड प्राप्त करना आसान नहीं था, जिसमें एशियाई चरित्र होते हैं, कुछ बदलाव करते हैं ( इसमें संकलन करना और उसका परीक्षण करना) और परिणाम को वापस भेजना, सभी को कुछ नुकसान पहुंचाए बिना।

तो, जावा स्रोत कोड किसी भी एन्कोडिंग में लिखा जा सकता है और पहचानकर्ताओं, चरित्र और String शाब्दिक और टिप्पणियों के भीतर पात्रों की एक विस्तृत श्रृंखला की अनुमति देता है। फिर, इसे दोषरहित रूप से स्थानांतरित करने के लिए, लक्ष्य एन्कोडिंग द्वारा समर्थित नहीं सभी वर्णों को उनके यूनिकोड से बदल दिया जाता है।

यह एक प्रतिवर्ती प्रक्रिया है और दिलचस्प बात यह है कि अनुवाद एक उपकरण द्वारा किया जा सकता है जिसे जावा स्रोत कोड सिंटैक्स के बारे में कुछ भी जानने की आवश्यकता नहीं है क्योंकि अनुवाद नियम इस पर निर्भर नहीं है। यह संकलक के अंदर उनके वास्तविक यूनिकोड वर्णों के अनुवाद के रूप में काम करता है जो स्वतंत्र रूप से जावा स्रोत कोड सिंटैक्स के साथ भी होता है। इसका तात्पर्य है कि आप स्रोत कोड के अर्थ को बदलने के बिना दोनों दिशाओं में अनुवाद चरणों की एक मनमानी संख्या कर सकते हैं।

यह एक और अजीब विशेषता का कारण है जिसका उल्लेख भी नहीं किया गया है: \uuuuuuxxxx वाक्यविन्यास:

जब कोई अनुवाद टूल वर्णों से बच रहा है और पहले से ही बचा हुआ अनुक्रम का सामना करता है, तो उसे \ucafe को \uucafe परिवर्तित करके अनुक्रम में एक अतिरिक्त u सम्मिलित करना चाहिए। अर्थ नहीं बदलता है, लेकिन जब दूसरी दिशा में परिवर्तित होता है, तो उपकरण को केवल एक u हटा देना चाहिए और केवल यूनिकोड वर्णों द्वारा एकल u वाले अनुक्रमों को प्रतिस्थापित करना चाहिए। इस तरह, यहां तक ​​कि यूनिकोड से बचकर आगे और पीछे जाने पर अपने मूल रूप में बच जाते हैं। मुझे लगता है, कोई भी कभी भी उस सुविधा का उपयोग करता है ...


मैं पूरी तरह से अप्रभावी रूप से इस बिंदु को जोड़ने जा रहा हूं, सिर्फ इसलिए कि मैं अपने आप को मदद नहीं कर सकता हूं और मैंने इसे अभी तक नहीं देखा है, क्योंकि यह प्रश्न अमान्य है क्योंकि इसमें एक छिपा हुआ आधार है जो गलत है, अर्थात कोड में है एक टिप्पणी!

जावा स्रोत में कोड \ u000d हर तरह से एक ASCII CR वर्ण के बराबर है। यह जहां कहीं भी होता है, एक लाइन समाप्त करने वाला, सादा और सरल होता है। प्रश्न में प्रारूपण भ्रामक है, वर्णों का वह क्रम वास्तव में किसके अनुरूप है:

public static void main(String... args) {
   // The comment below is no typo. 
   // 
 System.out.println("Hello World!");
}

IMHO सबसे सही उत्तर इसलिए है: कोड निष्पादित होता है क्योंकि यह एक टिप्पणी में नहीं है; यह अगली पंक्ति पर है। जावा में "टिप्पणियों में निष्पादन की अनुमति नहीं है", जैसे आप उम्मीद करेंगे।

अधिकांश भ्रम इस तथ्य से उपजा है कि सिंटैक्स हाइलाइटर्स और आईडीई इस स्थिति को ध्यान में रखने के लिए पर्याप्त परिष्कृत नहीं हैं। वे या तो यूनिकोड से बचने की प्रक्रिया नहीं करते हैं, या वे पहले के बजाय कोड को पार्स करने के बाद ऐसा करते हैं, जैसे कि javac करता है।


यह एक जानबूझकर डिजाइन पसंद था जो जावा के मूल डिजाइन पर वापस जाता है।

उन लोगों के लिए जो पूछते हैं "जो यूनिकोड टिप्पणी में भागना चाहते हैं?", मुझे लगता है कि वे ऐसे लोग हैं जिनकी मूल भाषा लैटिन वर्ण सेट का उपयोग करती है। दूसरे शब्दों में, यह जावा के मूल डिज़ाइन में अंतर्निहित है कि लोग एक यूनिकोड वर्णों का उपयोग कर सकते हैं जहाँ कोई जावा प्रोग्राम में कानूनी रूप से, सबसे अधिक टिप्पणियों और तार में।

यह निश्चित रूप से उन कार्यक्रमों में कमी है (जैसे आईडीई) स्रोत पाठ को देखने के लिए उपयोग किया जाता है कि ऐसे कार्यक्रम यूनिकोड से बच नहीं सकते हैं और संबंधित ग्लिफ़ को प्रदर्शित कर सकते हैं।


संकलक न केवल यूनिकोड का अनुवाद करता है उन पात्रों में भाग जाता है जो वे प्रतिनिधित्व करते हैं इससे पहले कि यह एक कार्यक्रम को टोकन में पार्स करता है, लेकिन यह टिप्पणियों और सफेद स्थान को छोड़ने से पहले ऐसा करता है।

इस कार्यक्रम में एक एकल यूनिकोड एस्केप (\ u000d) शामिल है, जो इसकी एकमात्र टिप्पणी में स्थित है। जैसा कि टिप्पणी आपको बताती है, यह पलायन लाइनफीड चरित्र का प्रतिनिधित्व करता है, और संकलक टिप्पणी को छोड़ने से पहले इसका विधिवत अनुवाद करता है।

यह प्लेटफॉर्म पर निर्भर है। कुछ प्लेटफार्मों पर, जैसे UNIX, यह काम करेगा; दूसरों पर, जैसे कि विंडोज, यह नहीं होगा। हालांकि आउटपुट नग्न आंखों के समान हो सकता है, यह आसानी से समस्याओं का कारण बन सकता है अगर इसे एक फ़ाइल में सहेजा गया या बाद के प्रसंस्करण के लिए किसी अन्य प्रोग्राम में पाइप किया जाए।


\u000d बचना एक टिप्पणी को समाप्त कर देता है क्योंकि \u एस्केप प्रोग्राम के टोकन होने से पहले समान रूप से यूनिकोड वर्ण में परिवर्तित हो जाते हैं। आप एक टिप्पणी शुरू करने के लिए // बजाय समान रूप से \u0057\u0057 उपयोग कर सकते हैं।

यह आपके IDE में एक बग है, जिसे यह स्पष्ट करने के लिए लाइन को सिंटैक्स-हाइलाइट करना चाहिए कि \u000d टिप्पणी समाप्त होती है।

यह भाषा में एक डिज़ाइन त्रुटि भी है। इसे अब ठीक नहीं किया जा सकता है, क्योंकि यह उन कार्यक्रमों को तोड़ देगा जो इस पर निर्भर हैं। \u एस्केप को या तो कंपाइलर द्वारा संबंधित यूनिकोड चरित्र में केवल संदर्भों में परिवर्तित किया जाना चाहिए, जहां "समझ में आता है" (स्ट्रिंग शाब्दिक और पहचानकर्ता, और शायद कहीं और) या उन्हें U + 0000- में वर्ण उत्पन्न करने के लिए मना किया जाना चाहिए था 007F रेंज, या दोनों। या तो उन शब्दार्थों ने टिप्पणी को \u000d एस्केप द्वारा समाप्त होने से रोका होगा, उन मामलों के साथ हस्तक्षेप किए बिना, जहां \u एस्केप उपयोगी हैं - ध्यान दें कि टिप्पणियों के अंदर \u एस्केप का उपयोग शामिल है एक टिप्पणी में एनकोड करने के तरीके के रूप में -लिटिन स्क्रिप्ट, क्योंकि टेक्स्ट एडिटर व्यापक दृष्टिकोण ले सकता है जहां कंपाइलर की तुलना में \u एस्केप महत्वपूर्ण हैं। (मैं किसी भी संपादक या आईडीई के बारे में नहीं जानता जो किसी भी संदर्भ में संबंधित पात्रों के रूप में प्रदर्शित होगा, हालांकि)

सी परिवार में एक समान डिजाइन त्रुटि है, 1 जहां बैकस्लैश-न्यूलाइन को टिप्पणी सीमाओं को निर्धारित करने से पहले संसाधित किया जाता है, इसलिए उदाहरण के लिए।

// this is a comment \
   this is still in the comment!

मैं इसे स्पष्ट करने के लिए लाता हूं कि यह विशेष रूप से डिज़ाइन त्रुटि करना आसान होता है, और यह महसूस नहीं करना कि यह एक त्रुटि है जब तक कि इसे ठीक करने के लिए बहुत देर हो चुकी है, यदि आप टोकन के बारे में सोचने और कंपाइलर प्रोग्रामर के सोचने के तरीके के बारे में सोचते हैं टोकन और पार्सिंग के बारे में। मूल रूप से, यदि आपने पहले से ही अपने औपचारिक व्याकरण को परिभाषित कर लिया है और फिर कोई व्यक्ति एक विशेष वाक्य-विशेष, ट्रिग्राफ, बैकस्लैश-न्यूलाइन के साथ आता है, तो ASCII तक सीमित स्रोत फ़ाइलों में मनमाने ढंग से यूनिकोड वर्णों को कूटबद्ध करना, जो भी - जिसको भी इसमें करने की आवश्यकता है, यह आसान है। टोकेनाइज़र से पहले एक परिवर्तन पास को जोड़ने की तुलना में उस टोकन को फिर से परिभाषित करना है जहां इस विशेष मामले का उपयोग करने के लिए समझ में आता है।

1 बालकों के लिए: मुझे पता है कि C का यह पहलू 100% जानबूझकर था, औचित्य के साथ - मैं इसे नहीं बना रहा हूं - कि यह आपको पंच कार्डों पर मनमाने ढंग से लंबी लाइनों के साथ यंत्रवत्-फिट कोड की अनुमति देगा। यह अभी भी एक गलत डिजाइन निर्णय था।






comments