आपको "गरीब आदमी" में दिलचस्पी हो सकती है find:
shopt -s globstar
shopt -s s शेल विकल्प का नाम ets है। globstarविकल्प में इस प्रकार परिभाषित किया गया है बैश (1) :
यदि सेट **किया जाता है , तो फ़ाइल नाम / pathname विस्तार संदर्भ में उपयोग किया जाने वाला पैटर्न एक फाइलों [sic] और शून्य या अधिक निर्देशिकाओं और उपनिर्देशिकाओं से मेल खाएगा । यदि पैटर्न के बाद ए /, केवल निर्देशिका और उपनिर्देशिका मेल खाते हैं।
इसलिए, आपके द्वारा किए जाने के बाद shopt -s globstar, निम्न में से कोई भी आदेश:
ls -d1 - source / ** # 'd' के बाद का वर्ण अंक एक है।
ls -d - स्रोत / ** | बिल्ली # यानी, यह किसी भी कमांड को पाइप में लिख देगा।
प्रिंटफ "% s \ n" स्रोत / **
उत्पादन का उत्पादन होगा:
source/
source/fonts
source/fonts/fontello
source/images
source/images/bg1.png
source/images/eng.png
source/images/fra.png
दुर्भाग्य से, इसमें निर्देशिका नाम भी शामिल हैं। यह जानने में आपको थोड़ी मदद मिल सकती है
printf "%s\n" source/**/
उत्पादन का उत्पादन होगा:
source/
source/fonts
source/images
यानी, केवल निर्देशिका नाम। आप एक फ़ाइल में कमांड के पहले सेट के आउटपुट को रीडायरेक्ट कर सकते हैं, ऊपर के आउटपुट को एक दूसरी फ़ाइल पर रीडायरेक्ट कर सकते हैं, और फिर पहले वाले से दूसरी फ़ाइल को हटाने के लिए, या कुछ इसी तरह का उपयोग कर सकते हैं comm, diffकेवल सादा छोड़कर। फ़ाइलें (गैर-निर्देशिका)। लेकिन ऐसा मत करो।
एक और दृष्टिकोण (जो वह नहीं है ज्यादा बेहतर) है
ls -d --file-type -- source/** | grep -v '/$'
--file-typeविकल्प बताता है lsएक प्रदर्शित करने के लिए /
प्रत्येक निर्देशिका का नाम (और अन्य (विशेष के सिरों) फ़ाइल प्रकारों में अन्य वर्ण), इस तरह के अंत में:
source // # एक अतिरिक्त एक
स्रोत / फोंट / # एक जोड़ा गया
स्रोत / फोंट / fontello
स्रोत / चित्र / # एक जोड़ा गया
स्रोत / images / bg1.png
स्रोत / images / eng.png
स्रोत / images / fra.png
और फिर उन grep -v '/$'रेखाओं को हटा देता है जो समाप्त होती हैं /; यानी, निर्देशिका के नाम। दुर्भाग्य से, --file-typeविकल्प POSIX द्वारा निर्दिष्ट नहीं है । यदि आपका संस्करण lsइसका समर्थन नहीं करता है, तो उपयोग करें -F। यह ऐसा है जैसे कि --file-type
यह *निष्पादन योग्य फ़ाइलों के नामों के सिरों पर भी प्रदर्शित होता है, जो कुछ लोगों को कष्टप्रद लगता है। आप उन्हें समाप्त कर सकते हैं sed:
ls -dF -- source/** | sed -e '/\/$/d' -e 's/\*$//'
यदि आप सभी फाइलों (और केवल फाइलों) के साथ कुछ करना चाहते हैं, तो आप कर सकते हैं
f के लिए स्रोत / **
कर
अगर [-f "$ f"]
फिर
समतल फ़ाइलों पर लागू होने वाली कमांड डालें।
फाई
किया हुआ
टिप्पणियाँ:
- जब
lsएक टर्मिनल पर आउटपुट किया जाता है, और यह -l( एल ओएनजी) मोड में नहीं है, तो यह प्रति लाइन कई नाम लिखता है (जब तक कि नाम बहुत लंबा नहीं है)। आप इसे प्रति पंक्ति एक नाम निर्दिष्ट करके -1(एक), या आउटपुट को फ़ाइल या पाइप पर रीडायरेक्ट करके लिख सकते हैं ।
- जब से आप एक ऐसी निर्देशिका को सूचीबद्ध कर रहे हैं जिसकी सामग्री आपने बनाई है, तो आपको वास्तव
--में lsआदेशों की आवश्यकता नहीं है । *अज्ञात निर्देशिका में सूचीबद्ध होने पर आपको इसका उपयोग करना चाहिए , क्योंकि शुरू होने वाले फ़ाइल नाम के खिलाफ सुरक्षा -।
- से आउटपुट पार्स करने की कोशिश मत करो
ls।
globstarखोल विकल्प POSIX से परिभाषित किया जा करने के लिए नहीं दिखाई देता है। (वास्तव में, मुझे यकीन नहीं है कि पोसिक्स किसी भी शेल विकल्पों को पहचानता है ।) जबकि यह एक bashism, beware लगता है - यह बैश के सभी संस्करणों में मौजूद नहीं हो सकता है।
यदि fontsया imagesउपनिर्देशिकाएँ हैं, **तो उन सभी को, पुनरावर्ती, सभी तरह से नीचे सूचीबद्ध करेगा। गहराई को सीमित करने का एक (कुछ हद तक कीचड़ और अविश्वसनीय) तरीका है
ls -d --file-type -- source/** | grep -v '\(/.*\)\{3\}'
जो तीन या अधिक /वर्ण वाली रेखाओं को हटाता है ।
findगलत तरीके से भी उपयोग करने के तरीके हैं ; विशेष रूप से, यदि आप दौड़ रहे हैंfor file in $(find ...), तो आपने उनमें से एक को मारा है)।