एक ही समय में एक निर्देशिका में कई फ़ाइलों का नाम बदलने के लिए कैसे


12

मेरे पास निर्देशिका है /var/tmp/abcजिसमें 4 फाइलें हैं:

12345-ram-3e3r5-io9490-89adu9.csv
45434-dam-qwe35-to9490-43adu9.csv
11234-cam-yy3r5-ro9490-85adu9.csv
14423-sam-hh3r5-uo9490-869du9.csv

मैं सभी CSV फ़ाइलों का नाम बदलना चाहता हूं (सभी फाइलें ढूंढें और उन्हें नाम बदलें) कम से कम संभव (शायद एक-लाइनर) इस तरह से:

XXXXX-ram-3e3r5-io9490-89adu9.csv
XXXXX-dam-qwe35-to9490-43adu9.csv
XXXXX-cam-yy3r5-ro9490-85adu9.csv
XXXXX-sam-hh3r5-uo9490-869du9.csv

जवाबों:


15

rename -n 's/(\w+)/XXXXX/' *.csv

-nखुश होने पर हटा दें ।


2
के एक उपयुक्त संस्करण के लिए rename। मुझे लगता है कि यह लैरी वॉल का है rename, renameडेबियन में पैकेज और व्युत्पन्न (और prenameरेडहैट अनुनय की प्रणालियों पर IIRC )। एक बहुत ही उपयोगी उपकरण।
xenoid

2
perl-renameमेहराब में
lesmana

1
@SHawarden, मैंने कमांड को निष्पादित करने की कोशिश की है और प्रतिस्थापित पैटर्न को समझने के लिए मैन पेज के संबंधित हिस्से को पढ़ा है, लेकिन verboseझंडा जोड़ने पर , यह कुछ भी आउटपुट नहीं करता है और फ़ाइल नाम में परिवर्तन नहीं करता है, भले ही वर्तमान पथ हो। के समान नाम वाली फाइलें 12345_foo.csv। क्या मुझे इसे काम करने के लिए कोई अतिरिक्त कार्य करना होगा (वर्तमान में फेडोरा 30 पर)? यह लूपिंग की तुलना में एक क्लीनर दृष्टिकोण है। अग्रिम में धन्यवाद!
danieldeveloper001

3
@ danieldeveloper001 क्या आपने उपयोग किया renameया prename? ऊपर मेरी टिप्पणी देखें। man {the command}अंत में लेखकों को सूचीबद्ध करता है।
xenoid

2
यह केवल डेबियन-व्युत्पन्न सिस्टम पर काम करता है। फेडोरा-व्युत्पन्न सिस्टम में एक पूरी तरह से अलग renameकमांड है; देखें unix.stackexchange.com/a/238862/135943
वाइल्डकार्ड

11

प्रयत्न:

for f in *.csv; do mv -i -- "$f" "XXXXX-${f#*-}"; done

यह काम किस प्रकार करता है:

  • for f in *.csv; do

    यह सभी *.csvफाइलों पर लूप शुरू करता है।

  • mv -i -- "$f" "XXXXX-${f#*-}"

    यह किसी भी फ़ाइल को अधिलेखित करने से पहले इंटरएक्टिव तरीके से पूछते हुए फ़ाइलों का नाम बदल देता है।

  • done

    यह लूप के अंत को चिह्नित करता है।

उदाहरण:

$ ls -1
11234-cam-yy3r5-ro9490-85adu9.csv
12345-ram-3e3r5-io9490-89adu9.csv
14423-sam-hh3r5-uo9490-869du9.csv
45434-dam-qwe35-to9490-43adu9.csv
$ for f in *.csv; do mv -i -- "$f" "XXXXX-${f#*-}"; done
$ ls -1
XXXXX-cam-yy3r5-ro9490-85adu9.csv
XXXXX-dam-qwe35-to9490-43adu9.csv
XXXXX-ram-3e3r5-io9490-89adu9.csv
XXXXX-sam-hh3r5-uo9490-869du9.csv

4

मुझे आपके द्वारा पोस्ट की गई छोटी सी चुनौती पसंद आई, इसलिए यहां मेरा समाधान है। मैं यह मान रहा हूं कि आपकी सभी फाइलें 5 संख्यात्मक वर्णों से शुरू होती हैं, इसलिए प्रारंभिक संख्यात्मक फाइलों को "XXXXX" द्वारा बदलने के लिए कट कमांड का उपयोग किया जाता है

नीचे, कमांड से पहले फाइलें।

-rw-rw-r--. 1 daniel daniel 0 May 13 23:18 11111_bar_file.csv
-rw-rw-r--. 1 daniel daniel 0 May 13 22:54 12345_baz_file.csv
-rw-rw-r--. 1 daniel daniel 0 May 13 22:54 67890_foo_file.xml

नीचे, एक लाइनर कमांड।

for src in *.csv; do dst=XXXXX$(echo $src| cut -c6-); mv $src $dst; done;

नीचे, कमांड के बाद फाइलें।

-rw-rw-r--. 1 daniel daniel 0 May 13 22:54 67890_foo_file.xml
-rw-rw-r--. 1 daniel daniel 0 May 13 22:54 XXXXX_bar_file.csv
-rw-rw-r--. 1 daniel daniel 0 May 13 23:18 XXXXX_baz_file.csv

कि तुम क्या देख रहे हो? :)

संदर्भ:

बाश में कमांड आउटपुट के माध्यम से लूपिंग

मारपीट में तोड़फोड़ की


2
बैश इस तरह के स्ट्रिंग हेरफेर कर सकते हैं, प्रत्येक के लिए एक नई प्रक्रिया को कांटा करने की आवश्यकता नहीं है, कृपया अन्य उत्तर कैसे दें।
chx

1
@chx, पहले से ही अन्य उत्तरों को देख चुका है और इससे थोड़ा बहुत ज्ञान प्राप्त कर लिया है, लेकिन उन्हें इंगित करने के लिए धन्यवाद। क्या आप कृपया विस्तार से बताएंगे no need to fork a new process for each?
danieldeveloper001

3
cutएक अलग बाइनरी ( /usr/bin/cut) है और इसे चलाने से शेल निर्मित इन का उपयोग करने की तुलना में अधिक संसाधनों की खपत होती है।
chx

2
मैं देखता हूं, यह वास्तव में मायने रखता है कि क्या इरादे बहुत सारी फाइलों का नाम बदल रहे हैं। सफाई देने के लिए धन्यवाद!
danieldeveloper001

1

कोई कांटा नहीं:

ls | perl -lne '$suf=substr($_,6); rename $_, "XXXXX-$suf"'

जब आप शेल लूप का उपयोग करते हैं, तो mvफ़ाइल के अनुसार एक बार कांटे। पर्ल की renameआज्ञा नहीं है।

(पर्ल के नाम बदलने के आदेश में कुछ प्रतिबंध हैं, लेकिन इस विशिष्ट मामले में वे प्रतिबंध लागू नहीं होते हैं।)

जैसा renameकि पहले दिखाया गया कमांड के लिए , हां जो काम करता है, लेकिन फिर आपके पास दो अलग-अलग प्रकार के नाम बदलने और इसी तरह की उलझन है। यदि आपके पास सही है, महान है, लेकिन यदि नहीं, तो यह भी काम करता है।

यदि आपके पास perl-rename कमांड नहीं है और इसे स्थापित नहीं कर सकते हैं, तो आप यह कर सकते हैं:

ls | perl -lne '$old=$_; s/(\w+)/XXXXX/; rename $old, $_'

जैसा कि आप देख सकते हैं, यह शीर्ष उत्तर में दिखाए गए समान प्रतिस्थापन का उपयोग करता है। बेशक पर्ल नाम बदलने अन्य घंटियां और सीटियां (ऊपर जवाब उल्लेख किया है, है -nपहले से ही है, तो वहाँ -0, -f, और इतने पर), और उनमें से अधिक आप की जरूरत है, और अधिक आपको लगता है कि अपनी खुद की इस तरह से स्थापित करना चाहिए बजाय रोलिंग ।


एक पाइप के सामान्य कार्यान्वयन में कांटे होंगे।
मुरु

मेरा मतलब था, "फ़ाइल का नाम एक बार कांटा नहीं जाएगा", यहाँ तक कि शेल के विपरीत, जहाँ "mv" कांटे / usr / bin / mv या जो भी हो। इसका कारण यह है कि "नाम बदलना" कमांड एक पर्ल आंतरिक कमांड है जो सीधे तौर पर नाम बदलने () को libc में कॉल करता है। बेशक इसमें कुछ प्रतिबंध हैं, लेकिन इस विशिष्ट उदाहरण में वे प्रतिबंध लागू नहीं होते हैं।
सीताराम

1
यह भी renameआदेश का सच है ( शीर्ष उत्तर , पर्ल का उपयोग भी करता है), इसलिए शायद आपको उत्तर के लिए बस "कोई कांटे" की तुलना में थोड़ा अधिक स्पष्टीकरण जोड़ना चाहिए।
मुरु
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.