शुरुआती गाइड टू शैल स्क्रिप्टिंग 2: लूप्स के लिए

विषयसूची:

शुरुआती गाइड टू शैल स्क्रिप्टिंग 2: लूप्स के लिए
शुरुआती गाइड टू शैल स्क्रिप्टिंग 2: लूप्स के लिए

वीडियो: शुरुआती गाइड टू शैल स्क्रिप्टिंग 2: लूप्स के लिए

वीडियो: शुरुआती गाइड टू शैल स्क्रिप्टिंग 2: लूप्स के लिए
वीडियो: How to Fix Missing Suggestion Strip on Gboard (Google Keyboard)? - YouTube 2024, जुलूस
Anonim
यदि आप अपना गीक क्रेडिट बनाना चाहते हैं, तो हमारी शेल स्क्रिप्टिंग श्रृंखला में दूसरी किस्त के लिए हमसे जुड़ें। हमारे पास कुछ सुधार हैं, पिछले हफ्ते की लिपि में कुछ सुधार हैं, और अनियमित के लिए लूपिंग पर एक गाइड है।
यदि आप अपना गीक क्रेडिट बनाना चाहते हैं, तो हमारी शेल स्क्रिप्टिंग श्रृंखला में दूसरी किस्त के लिए हमसे जुड़ें। हमारे पास कुछ सुधार हैं, पिछले हफ्ते की लिपि में कुछ सुधार हैं, और अनियमित के लिए लूपिंग पर एक गाइड है।

डेटसीपी स्क्रिप्ट Revisited

हमारी शेल स्क्रिप्टिंग मार्गदर्शिका की पहली किस्त में, हमने एक स्क्रिप्ट बनाई जिसने फ़ाइल नाम के अंत तक तारीख को जोड़ने के बाद फ़ाइल को बैकअप निर्देशिका में कॉपी किया।

सैमुअल डायनने-रील ने टिप्पणियों में बताया कि हमारे परिवर्तनीय संदर्भों को संभालने का एक बेहतर तरीका है।

Arguments are space-separated in the bash shell, it will tokenize when there is a space in the resulted expanded command. In your script,

cp $1 $2.$date_formatted

तब तक कार्य करेगा जब तक विस्तारित चरों में रिक्त स्थान न हों। यदि आप अपनी स्क्रिप्ट को इस तरह कहते हैं:

datecp 'my old name' 'my new name'

इस आदेश में विस्तार का परिणाम होगा:

cp my new name my old name.the_date

वास्तव में 6 तर्क हैं।

इस समस्या को सही तरीके से संबोधित करने के लिए, स्क्रिप्ट की अंतिम पंक्ति होना चाहिए:

cp '$1' '$2.$date_formatted'

जैसा कि आप देख सकते हैं, हमारी स्क्रिप्ट की लाइन को बदलकर:

cp -iv $1 $2.$date_formatted

सेवा मेरे:

cp -iv “$1” “$2”.$date_formatted

नाम पर रिक्त स्थान वाली फ़ाइलों पर स्क्रिप्ट का उपयोग करते समय इस समस्या का ख्याल रखेगा। सैमुअल भी इस बात को इंगित करता है कि जब इस साइट (या सामान्य रूप से इंटरनेट) से कोड कॉपी और पेस्ट करना निश्चित रूप से "टाइपोग्राफ़िक रूप से बेहतर" लोगों के लिए उचित डैश और उद्धरण को प्रतिस्थापित करना सुनिश्चित करता है जो अक्सर उन्हें प्रतिस्थापित करते हैं। यह सुनिश्चित करने के लिए हम और भी कर रहे होंगे कि हमारा कोड अधिक प्रतिलिपि / पेस्ट अनुकूल है।;-)

एक और टिप्पणीकार, माइल्स ब्रीथवाइट ने हमारी स्क्रिप्ट का विस्तार करने का फैसला किया ताकि तिथि फ़ाइल एक्सटेंशन से पहले दिखाई दे। तो इसके बजाय

tastyfile.mp3.07_14_11-12.34.56

हम यह प्राप्त करेंगे:

tastyfile.07_14_11-12.34.56.mp3

जो ज्यादातर उपयोगकर्ताओं के लिए थोड़ा और सुविधाजनक होने के समाप्त होता है। उसका कोड उनके गिटहब पेज पर उपलब्ध है। आइए देखें कि वह फ़ाइल नाम को अलग करने के लिए क्या उपयोग करता है।

date_formatted=$(date +%Y-%m-%d_%H.%M%S) file_extension=$(echo “$1″|awk -F. ‘{print $NF}’) file_name=$(basename $1.$file_extension)

cp -iv $1 $file_name-$date_formatted.$file_extension

मैंने स्वरूपण को थोड़ा सा बदल दिया है, लेकिन आप देख सकते हैं कि माइल्स लाइन 1 में अपना दिनांक फ़ंक्शन घोषित करता है। हालांकि, लाइन 2 में, वह फ़ाइल के नाम को आउटपुट करने के लिए स्क्रिप्ट के पहले तर्क के साथ "गूंज" कमांड का उपयोग करता है। वह उस आउटपुट को लेने के लिए पाइप कमांड का उपयोग करता है और इसे अगले भाग के लिए इनपुट के रूप में उपयोग करता है। पाइप के बाद, माइल्स ने "awk" कमांड पर कॉल किया, जो एक शक्तिशाली पैटर्न स्कैनिंग प्रोग्राम है। -एफ ध्वज का उपयोग करके, वह आदेश को बता रहा है कि अगला चरित्र (एक स्थान के बाद) "फील्ड विभाजक" को परिभाषित करेगा। इस मामले में, यह एक अवधि है।

अब, "tastyfile.mp3" नाम की एक फ़ाइल को दो फ़ील्ड से बनाकर देखें: "tastyfile" और "mp3"। अंत में, वह उपयोग करता है

‘{print $NF}’

अंतिम क्षेत्र प्रदर्शित करने के लिए। यदि आपकी फ़ाइल में कई अवधि हैं - इसलिए बहुत से फ़ील्ड देखकर - यह केवल अंतिम दिखाएगा, जो फ़ाइल एक्सटेंशन है।

लाइन 3 में, वह फ़ाइल के नाम के लिए एक नया चर बनाता है और $ 1 में सबकुछ संदर्भित करने के लिए "बेसनाम" कमांड का उपयोग करता है के सिवाय फ़ाइल एक्सटेंशन। यह बेसनाम का उपयोग करके किया जाता है और इसे $ 1 को इसके तर्क के रूप में दिया जाता है, फिर एक स्थान और फ़ाइल एक्सटेंशन जोड़ता है। फाइल एक्सटेंशन को वैरिएबल के कारण स्वचालित रूप से जोड़ा जाता है जो रेखा 2 का संदर्भ देता है। यह क्या करेगा

tastyfile.mp3

और इसे चालू करें

tastyfile

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

चल रही लिपियों और $ पाथ

हम अपने मूलभूत लेख में भी उल्लेख करते हैं कि स्क्रिप्ट को डिफ़ॉल्ट रूप से कमांड के रूप में संदर्भित करने की अनुमति नहीं है। यही है, इसे चलाने के लिए आपको स्क्रिप्ट के पथ को इंगित करना होगा:

./script

~/bin/script

लेकिन, अपनी स्क्रिप्ट को ~ / bin / में रखकर, आप उन्हें चलाने के लिए कहीं भी अपने नाम टाइप कर सकते हैं।

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

यह फ़ाइल बैश द्वारा पढ़ी जाती है (जब तक.bash profile उपयोगकर्ता की होम निर्देशिका में मौजूद नहीं है) और नीचे, एक ऐसा अनुभाग है जो ~ / bin / फ़ोल्डर को $ PATH चर में जोड़ता है यदि यह मौजूद है। तो, वह रहस्य साफ हो गया है। श्रृंखला के बाकी हिस्सों के लिए, मैं ~ / bin / निर्देशिका में लिपियों को रखना जारी रखूंगा क्योंकि वे उपयोगकर्ता स्क्रिप्ट हैं और उपयोगकर्ताओं द्वारा संचालित होने में सक्षम होना चाहिए। और, ऐसा लगता है कि चीजों को काम करने के लिए हमें हाथ से $ PATH चर के साथ गड़बड़ करने की ज़रूरत नहीं है।
यह फ़ाइल बैश द्वारा पढ़ी जाती है (जब तक.bash profile उपयोगकर्ता की होम निर्देशिका में मौजूद नहीं है) और नीचे, एक ऐसा अनुभाग है जो ~ / bin / फ़ोल्डर को $ PATH चर में जोड़ता है यदि यह मौजूद है। तो, वह रहस्य साफ हो गया है। श्रृंखला के बाकी हिस्सों के लिए, मैं ~ / bin / निर्देशिका में लिपियों को रखना जारी रखूंगा क्योंकि वे उपयोगकर्ता स्क्रिप्ट हैं और उपयोगकर्ताओं द्वारा संचालित होने में सक्षम होना चाहिए। और, ऐसा लगता है कि चीजों को काम करने के लिए हमें हाथ से $ PATH चर के साथ गड़बड़ करने की ज़रूरत नहीं है।

लूप्स के साथ कमांड को दोहराएं

आइए दोहराए गए कार्यों से निपटने के लिए गीक शस्त्रागार में सबसे उपयोगी टूल में से एक प्राप्त करें: लूप। आज, हम "फॉर" लूप पर चर्चा करेंगे।

फॉर-लूप की मूल रूपरेखा निम्नानुसार है:

for VARIABLE in LIST; do command1 command2 … commandn done

VARIABLE कोई परिवर्तनीय हो सकता है, हालांकि अक्सर लोअरकेस "i" का उपयोग सम्मेलन द्वारा किया जाता है। सूची वस्तुओं की एक सूची है; आप एकाधिक वस्तुओं को निर्दिष्ट कर सकते हैं (उन्हें एक स्थान से अलग कर सकते हैं), बाहरी टेक्स्ट फ़ाइल को इंगित करें, या वर्तमान निर्देशिका में किसी भी फ़ाइल को इंगित करने के लिए तारांकन (*) का उपयोग करें। सूचीबद्ध आदेशों को सम्मेलन द्वारा इंडेंट किया गया है, इसलिए घोंसले को देखना आसान है - लूप में लूप डालना (ताकि आप लूप के दौरान लूप कर सकें)।

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

इसमें, निम्न कोड दर्ज करें:

for i in item1 item2 item3 item4 item5 item6; do echo “$i” done

जब आप स्क्रिप्ट चलाते हैं, तो आपको केवल उन सूची आइटम को आउटपुट के रूप में प्राप्त करना चाहिए।
जब आप स्क्रिप्ट चलाते हैं, तो आपको केवल उन सूची आइटम को आउटपुट के रूप में प्राप्त करना चाहिए।
बहुत आसान, है ना? चलो देखते हैं कि क्या होता है अगर हम चीजों को थोड़ा सा बदल देते हैं। अपनी स्क्रिप्ट बदलें ताकि यह कह सके:
बहुत आसान, है ना? चलो देखते हैं कि क्या होता है अगर हम चीजों को थोड़ा सा बदल देते हैं। अपनी स्क्रिप्ट बदलें ताकि यह कह सके:

for i in *; do echo “$i” done

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

for i in $@; do zip archive “$i” done

कुछ नया है! "$ @" "$ 1 $ 2 $ 3 … $ n" के लिए एक शॉर्टकट है। दूसरे शब्दों में, यह आपके द्वारा निर्दिष्ट सभी तर्कों की पूरी सूची है। अब, देखें कि जब मैं कई इनपुट फ़ाइलों के साथ स्क्रिप्ट चलाता हूं तो क्या होता है।
कुछ नया है! "$ @" "$ 1 $ 2 $ 3 … $ n" के लिए एक शॉर्टकट है। दूसरे शब्दों में, यह आपके द्वारा निर्दिष्ट सभी तर्कों की पूरी सूची है। अब, देखें कि जब मैं कई इनपुट फ़ाइलों के साथ स्क्रिप्ट चलाता हूं तो क्या होता है।
Image
Image

आप देख सकते हैं कि मेरे फ़ोल्डर में कौन सी फाइलें हैं। मैंने छह तर्कों के साथ कमांड चलाया, और प्रत्येक फ़ाइल को "archive.zip" नामक एक ज़िपित संग्रह में जोड़ा गया था। आसान, सही?

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

फॉर-लूप का उपयोग करना निर्देशिका में सभी फ़ाइलों के लिए कार्यों का एक गुच्छा करना आसान बनाता है। आप एक साथ विभिन्न प्रकार के आदेशों को ढेर कर सकते हैं और बनाने और ऑन-द-फ्लाई सूची बनाने के लिए तर्कों का आसानी से उपयोग कर सकते हैं, और यह केवल हिमशैल की नोक है।

बैश स्क्रिप्टर्स, क्या आपके पास कोई सुझाव है? क्या आपने एक उपयोगी स्क्रिप्ट बनाई है जो लूप का उपयोग करती है? श्रृंखला पर आपको विचार साझा करना चाहते हैं? कुछ टिप्पणियां छोड़ें और अन्य स्क्रिप्टिंग न्यूबीज की मदद करें!

सिफारिश की: