क्यों "इको-ई" कमांड सही आउटपुट का उत्पादन नहीं करते हैं?


21

जब मैं इस कमांड को लिखता हूं, तो Ubuntu 18.04 LTS के टर्मिनल में:

echo -e "Hello\\\n"

यह इसे आउटपुट के रूप में देता है:

Hello\n

लेकिन इसे प्रिंट करना चाहिए, जैसा कि मैन पेज कहता है:

Hello\

यही है, पहले प्रिंट Hello, फिर \, एक नई लाइन वर्ण (और फिर एक और नई पंक्ति)। समस्या कहाँ हे?

देखें ये कुछ echo -eकमांड और उनका आउटपुट :

man420@man420-X542UQ:~$ echo -e "HEllo\a\a\a\a\a\a\\\n"
HEllo\n
man420@man420-X542UQ:~$ echo -e "HEllo\\\n"
HEllo\n
man420@man420-X542UQ:~$ echo -e "HEllo\a\\\n"
HEllo\n

हां। पहले 2 \ के लिए यह a \। और अंतिम होना चाहिए और n एक बैकस्लैश एस्केप \ n (नई लाइन) बनाना चाहिए। क्यों इसे हैलो
योलीन 00

1
बिना उद्धरणों के इसे आज़माएं।
अंजेरिंगो 619

2
एलिया कगन द्वारा एक अद्भुत उत्तर प्रदान किया गया था, जिसे आपको स्वीकार करना चाहिए।
वैनेडियम

2
echoपहली जगह में उपयोग न करें : उपयोग करें printf
चेपर

2
हमेशा एकल उद्धरण का उपयोग करें यदि आप यह सुनिश्चित करना चाहते हैं कि आप जो लिखते हैं वह वही है जो तर्क के रूप में कमांड को दिया जाता है।
जियाको अल्जेटा

जवाबों:


29

शेल के उद्धृत नियमों के अनुसार, बैकस्लैश का उपचार विशेष रूप से किया जाता है echo -e, लेकिन पहले उन्हें कभी-कभी शेल द्वारा विशेष रूप से व्यवहार किया जाता है (जो इस मामले में है bash) ।

तर्क echoवास्तव में देखता है Hello\\nक्योंकि आप पास हो -eगए हैं echo, यह बैकस्लैश से बचता है, विशेष रूप से बचता है, और \\एक एकल में ढह जाता है \। फाइनल nबच नहीं जाता है, इसलिए यह सचमुच दिखाई देता है।

इसका कारण यह है कि, echoस्वयं के संचालन से पहले और अलग से , शेल कुछ संदर्भों में विशेष रूप से व्यवहार करता\ है, लेकिन अन्य नहीं। निर्विवाद \पात्रों को हमेशा विशेष रूप से व्यवहार किया जाता है, एकल-उद्धृत \ का कभी भी विशेष रूप से इलाज नहीं किया जाता है, लेकिन दोहरे-उद्धृत \ वर्णों का उपचार , जैसा कि आपके द्वारा चलाए गए आदेश में है, अधिक सूक्ष्म और जटिल है।

जब शेल एक कमांड में डबल-कोटेड टेक्स्ट का सामना "Hello\\\n"करता है, तो उसके साथ , यह \एक भागने चरित्र के रूप में व्यवहार करता है जब यह एक चरित्र से पहले होता है जो कि दोहरे उद्धरण के अंदर विशेष अर्थ हो सकता है और अन्यथा नहीं

  1. क्योंकि \कभी-कभी अंदर एक विशेष अर्थ होता है "", \जो तुरंत दूसरे से पहले होता \है, उस दूसरे को उद्धृत करने का प्रभाव होता है \। तो दोहरे उद्धरण चिह्नों के अंदर, पहले \\ढह जाते हैं \
  2. उन पहले दो \पात्रों के बाद , एक तीसरा \चरित्र है जो उन पहले दो से अप्रभावित है और जो एक से पहले है n। लेकिन nएक ऐसा चरित्र नहीं है जिसे कभी भी दोहरे उद्धरण के अंदर विशेष रूप से व्यवहार किया जाता है, इसलिए \इससे पहले कि इस स्थिति में विशेष रूप से व्यवहार नहीं किया जाता है। इस प्रकार \nरहता है \n

इसका प्रभाव यह है कि, दोहरे उद्धरण चिह्नों के \\\nरूप में व्याख्या की गई है \\n

जब echo -eदेखता है \\n, पहले \दूसरे से विशेष अर्थ निकालता है, तो उस पाठ के लिए शाब्दिक रूप से echoप्रिंट \nकरता है।


यदि आपका लक्ष्य Helloएक अतिरिक्त न्यूलाइन के साथ प्रिंट करना है, लेकिन कोई बैकस्लैश नहीं है (प्रश्न मूल रूप से इस बारे में अस्पष्ट था, साथ ही मुझे लगता है कि यह एक उपयोगी उदाहरण है), तो एक समाधान एक को दूर करना है \। अंत में एक अतिरिक्त newline के साथ echo -e "Hello\\n"आउटपुट रनिंग Hello

एक बेहतर समाधान एकल उद्धरणों का उपयोग करना और लिखना है echo -e 'Hello\n'। एकल उद्धरण उद्धरण का सबसे मजबूत रूप हैं। एक बेहतर समाधान आमतौर पर printfइसके बजाय उपयोग करना है echo, जो इस मामले में होगा printf 'Hello\n\n'

यदि आपका लक्ष्य Hello\बैकस्लैश सहित प्रिंट करना है, उसके बाद एक अतिरिक्त न्यूलाइन है , तो डबल-कोटेड दृष्टिकोण संभव है लेकिन बोझिल है। यह पता लगाने के लिए, काम पीछे की ओर: echo -eधर्मान्तरित \\करने के लिए \और \nएक नई पंक्ति के लिए, और डबल के हवाले से धर्मान्तरित \\करने के लिए \है, तो आप छह बैकस्लैश (साथ यह कर सकते हैं echo -e "Hello\\\\\\n"), क्योंकि \\nमें बदल जाता है \nकी वजह से एक बैकस्लैश एक और भागने। आप इसे पांच के साथ भी कर सकते हैं, क्योंकि \nजब \बच नहीं जाता है तो दोहरे-उद्धरण को बनाए रखता है।

यह एकल उद्धरण के लाभ को दर्शाता है: बस जो कुछ भी आप echo -eएकल उद्धरण के अंदर देखना चाहते हैं उसे डालें ( echo -e 'Hello\\\n')। printfयहाँ भी अच्छा है। एक विकल्प है printf 'Hello\\\n\n'। लेकिन जहां printfवास्तव में चमक है कि आप अतिरिक्त तर्कों में प्लग कर सकते हैं। आप उपयोग कर सकते हैं printf '%s\n\n' 'Hello\', जो दूसरे तर्क को सम्मिलित करता है (शाब्दिक Hello\क्योंकि एकल उद्धरण कुछ भी नहीं बदलता है) %s

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.