เพิ่มนามสกุลไฟล์ซ้ำ ๆ ในไฟล์ทั้งหมด


106

ฉันมีไดเร็กทอรีและไดเร็กทอรีย่อยสองสามรายการที่มีไฟล์ที่ไม่มีนามสกุลไฟล์ ฉันต้องการเพิ่มลง.jpgในไฟล์ทั้งหมดที่อยู่ในไดเร็กทอรีเหล่านี้ ฉันเคยเห็นสคริปต์ทุบตีสำหรับการเปลี่ยนนามสกุลไฟล์ แต่ไม่ใช่แค่การเพิ่ม ยังต้องเรียกซ้ำใครช่วยได้ไหม

คำตอบ:


229

คำสั่งทางเลือกที่ไม่มีการวนซ้ำอย่างชัดเจน ( man find):

find . -type f -exec mv '{}' '{}'.jpg \;

คำอธิบาย: สิ่งนี้จะค้นหาไฟล์ทั้งหมดแบบวนซ้ำ ( -type f) โดยเริ่มจากไดเร็กทอรีปัจจุบัน ( .) และใช้คำสั่ง move ( mv) กับแต่ละไฟล์ โปรดสังเกตคำพูดรอบ ๆ{}เพื่อให้ชื่อไฟล์ที่มีช่องว่าง (และแม้แต่ขึ้นบรรทัดใหม่ ... ) ได้รับการจัดการอย่างเหมาะสม


7
โดยเฉพาะอย่างยิ่งไฟล์นี้จะทำงานได้ดีขึ้นหากมีไฟล์จำนวนมากในโครงสร้างไดเร็กทอรี (ทำให้ bash รู้สึกไม่พอใจกับความยาวของรายการไฟล์ที่ต้องวนซ้ำ)
DrAl

@Al หากคุณอ้างถึงการforวนซ้ำที่ทำให้ทุบตีเพื่อทำซ้ำในรายการไฟล์นั่นไม่ถูกต้อง bash forloop จะออกmvคำสั่งแต่ละคำสั่งซ้ำ ๆ
nik

คำถาม: ขั้นfindแรกตั้งค่ารายการไฟล์ก่อนที่จะดำเนินการ-execคำสั่งหรือไม่? ฉันเดาอย่างนั้น แต่ต้องการให้ประเด็นนี้ชัดเจนก่อนที่จะเข้ารหัสลูปที่ไม่มีที่สิ้นสุด
Boldewyn

2
คำสั่งนี้จะค้นหาไฟล์ที่มีนามสกุลเช่นกัน นั่นคือสิ่งที่ OP ต้องการหรือไม่?
ghostdog74

1
@ ghostdog74: เนื่องจากเขายอมรับคำตอบนี้เห็นได้ชัดว่าข้างต้นเป็นกลลวง มิฉะนั้นดังที่คุณกล่าวไว้ด้านล่างการเพิ่ม-not -name "*.*"จะทำเคล็ดลับ
Stephan202

62

จะพบไฟล์ที่ไม่มีนามสกุลและเพิ่ม. jpg ของคุณ

find /path -type f -not -name "*.*" -exec mv "{}" "{}".jpg \;

สิ่งนี้จะให้ผลลัพธ์ที่ต้องการอย่างแน่นอน 99% ของเวลา +1
เล

9

นี่ช้าไปหน่อย แต่ฉันคิดว่าฉันจะเพิ่มวิธีแก้ปัญหาที่ดีกว่า (แม้ว่าอาจจะอ่านได้น้อยกว่า) ที่อาจจะเป็น:

find /path -type f -not -name "*.*" -print0 | xargs -0 rename 's/(.)$/$1.jpg/'

ใช้ find | xargsทั่วไปรูปแบบจะส่งผลให้การดำเนินการมีประสิทธิภาพมากขึ้นเนื่องจากคุณไม่ต้องแยกกระบวนการใหม่สำหรับแต่ละไฟล์

โปรดทราบว่าสิ่งนี้ต้องใช้การเปลี่ยนชื่อเวอร์ชันที่พบใน Distros ที่ปรุงแต่งด้วย Debian (aka prename) มากกว่าการเปลี่ยนชื่อแบบเดิม แม้ว่ามันจะเป็นสคริปต์ perl เล็ก ๆ ดังนั้นมันจะง่ายพอที่จะใช้คำสั่งด้านบนกับระบบใดก็ได้


4

แบบนี้,

for f in $(find . -type f); do mv $f ${f}.jpg; done

ฉันไม่คาดหวังว่าคุณจะมีชื่อไฟล์ที่คั่นด้วยช่องว่าง
หากคุณมีชื่อจะต้องได้รับการประมวลผลเล็กน้อย

หากคุณต้องการเรียกใช้คำสั่งจากไดเร็กทอรีอื่น
คุณสามารถแทนที่find .ด้วยfind /target/directory.


1
สิ่งนี้ไม่มี 'do' และหากมีช่องว่างในชื่อไฟล์ควรอ้างอิงชื่อไฟล์: สำหรับ f ใน $ (find. -type f); ทำ mv "$ f" "$ {f} .jpg"; เสร็จแล้ว
DrAl

และน่าจะเรียกใช้จากภายในไดเรกทอรีระดับบนสุด?
robjmills

@seengee: ใช่ โปรดทราบว่าคำสั่งนี้ยังไม่มีเครื่องหมายขีดกลาง-typeด้วย
Stephan202

ฉันต้องไปที่ไหนสักแห่งและพิมพ์เร็วเกินไป ... กำลังแก้ไขตอนนี้
nik

1

สำหรับการเปลี่ยนชื่อไฟล์ทั้งหมดที่ไม่มีนามสกุลใน Windows พื้นฐานคุณสามารถทำได้ren * *.jpg เนื่องจากไฟล์ไม่มีนามสกุลให้ใช้ * หรือถ้าคุณต้องการเปลี่ยน png เป็น jpg ให้ใช้ren *.png *.jpg


0

rename

ไม่แน่ใจว่าสามารถเปลี่ยนชื่อไฟล์ที่ไม่มีนามสกุลได้ (ตอนนี้ฉันใช้ windows 7)


1
ทำได้ แต่จะเปลี่ยนชื่อไดเรกทอรีด้วยและไม่มีวิธีใดที่จะบอกให้ทำงานซ้ำในไดเรกทอรีย่อย (อย่างน้อยก็กับเวอร์ชันที่ฉันมีบน Ubuntu)
mirod

ฉันรู้คำสั่งที่แตกต่างกันอย่างน้อยสองคำที่เรียกว่าrenameหนึ่งโปรแกรม C รวมอยู่ใน util-linux-ng และหนึ่งโปรแกรม Perl (โดย Wall เอง) บนเครื่อง Debian ของมหาวิทยาลัยของเรา อันที่จริงไม่มีการเรียกซ้ำทั้งคู่
Boldewyn
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.