इस शेल स्क्रिप्ट में बैकस्लैश को क्यों शामिल किया गया है?


21

conda.shस्क्रिप्ट की मेरी प्रति में , मुझे निम्नलिखित पंक्तियाँ दिखाई देती हैं:

if [ -n "${_CE_CONDA}" ] && [ -n "${WINDIR+x}" ]; then
    SYSP=$(\dirname "${CONDA_EXE}")
else
    SYSP=$(\dirname "${CONDA_EXE}")
    SYSP=$(\dirname "${SYSP}")
fi

मुझे इस बात की उत्सुकता है कि क्यों अंदर में एक बैकस्लैश dहै dirname। मुझे विश्वास नहीं है कि यह आवश्यक है। स्रोत फ़ाइल में अन्य स्थानों पर भी बैकस्लैश का यह उपयोग दिखाई देता है। क्या ऐसा करने का कोई कारण है जो मुझे याद आ रहा है?


जवाबों:


30

बैकस्लैश उर्फ ​​विस्तार को दबा देगा, अर्थात यह मूल कमांड को निष्पादित करता है और सुनिश्चित करता है कि उपनाम संस्करण नहीं चलता है। लिपियों को अनजाने में उर्फ ​​विस्तार के साथ चलाया जा सकता है जब सिस्टम ने सेट किया है shopt -s expand_aliases(केवल BASH) या यदि इसका उपयोग करके निष्पादित किया जाता है source

./conda.sh          # usually no alias expansion (unless `shopt -s expand_aliases` in BASH)
source ./conda.sh   # alias expansion
. ./conda.sh        # alias expansion

कुछ sysadmins एलियंस के साइड-इफेक्ट के खिलाफ एक निवारक उपाय के रूप में हर चीज में बैकस्लैश डालना पसंद करते हैं, बस इस मामले में यह अनजाने में कहीं और अलियास हो गया था और उर्फ ​​विस्तार हो गया जैसा कि पहले बताया गया है। उदाहरण के लिए, यदि सिस्टम ने इसे alias dirname='dirname -z'कहीं सेट किया है और स्थिति उपनाम को विस्तारित करने की अनुमति देती है, तो एक स्क्रिप्ट जो कि dirname को कॉल करने का प्रयास करती है dirname -z, दुर्भाग्य से इसके बजाय कॉल करेगी , जो स्क्रिप्ट का इरादा नहीं था।

यदि निश्चितता है कि ऐसे उपनाम मौजूद नहीं हैं, तो हम सभी बैकस्लैश को हटा सकते हैं और इसे ठीक काम करना चाहिए।

वैकल्पिक रूप से, एक commandउपनाम को दबाने के लिए बैकस्लैश संस्करण के बजाय उपयोग कर सकता है । इस प्रकार, इसके बजाय \dirname, कोई भी उपयोग कर सकता है command dirname, जो अधिक पठनीय लग सकता है। (जैसे अंतर्निहित कमांड के लिए cd, व्यक्ति को builtinइसके बजाय उपयोग करना चाहिए )। मैं इसके बजाय इसे पसंद करता हूं, क्योंकि यह एक ही नाम के साथ-साथ किसी भी उपनाम के साथ फ़ंक्शन को भी बायपास करता है।


1
इसके अलावा ध्यान देने योग्य है unalias -a, जो सभी उपनामों को हटा देता है।
सेंटिमेन

19
@ सेंटिमेन ने हां लेकिन \unalias -aउर्फ विस्तार को दबाने के लिए करना सुनिश्चित करें
बेन सी

क्या सिसादमिन भी लिख सकता था /usr/bin/dirname?
रॉनजॉन

@RonJohn हाँ वह इस विशेष मामले में हो सकता है। हालांकि, कुछ कार्यक्रमों के लिए अलग-अलग वितरणों ने उन्हें अलग-अलग निर्देशिकाओं में रखा। एक उदाहरण जो मन में आता है वह /bin/edउबंटू बनाम /usr/bin/edसेंटोस पर है। पूर्ण पथ में डालने से स्क्रिप्ट कम पोर्टेबल हो जाती है।
doneal24

@ doneal24 क्या कुछ के बारे में पसंद है DIRNAME=$(which dirname), क्योंकि whichउपनाम नहीं देखता है?
रॉनजॉन

20

यदि conda.shएक फाइल को खट्टा किया जाना है, तो बैकस्लैश उपनामों को दरकिनार करने के लिए हैं। बैश आम तौर पर स्क्रिप्ट निष्पादन के लिए उर्फ ​​विस्तार को अक्षम करता है, लेकिन खट्टा फाइलों के लिए, जो इंटरैक्टिव गोले में चल सकता है, ऐसी बात नहीं है। तो बस dirnameनाम का एक उपनाम चला सकता है dirname, लेकिन \dirnameउपनाम को छोड़ देगा और नाम या फ़ंक्शन या कमांड चलाएगा dirname। (सिर्फ बैकस्लैश नहीं है, हालांकि, कोई भी उद्धरण करेगा।)


5
या command dirname
Kusalananda

7
( \command dirname, बस के मामले में किसी के commandरूप में अच्छी तरह से एक उपनाम बनाया है ।): |
मुरु

यह उपनामों को बायपास क्यों करता है? क्या यह कार्यक्षमता किसी चीज़ का एक विशेष मामला है, या क्या इसे बैश (यानी एक हैक) में हार्डकोड किया जाना है?
एक्सटैक्सएक्स 5

@ extremeaxe5 बैश उपनाम का विस्तार नहीं करता है अगर (किसी भी भाग) शब्द उद्धृत किया जाता है।
मुरु

1
@ extremeaxe5 यदि आप पूछ रहे हैं कि यह सुविधा क्यों मौजूद है, तो मुझे नहीं पता। हालांकि यह POSIX मानक में है : "कमांड नाम शब्द [...] यह निर्धारित करने के लिए जांच की जाएगी कि क्या यह एक अयोग्य , वैध उपनाम नाम है"
मुरु
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.