วิธีการกระจายหลายไฟล์ข้ามไดเรกทอรี?


19

ฉันพยายามค้นหาdiffไฟล์ทั้งหมดที่มีชื่อเหมือนกันในไดเรกทอรีสองชุด (พูดว่าใช้งานได้และสำรองข้อมูล) ตัวอย่างเช่นฉันสามารถdiffสองไฟล์ชื่อเดียวกันในทั้งสอง:

> diff d1/f.cpp d2/f.cpp

หรือฉันสามารถค้นหาความแตกต่างในไดเรกทอรี:

> diff d1 d2

แต่ฉันจะค้นหาความแตกต่างระหว่าง*.cppไฟล์เท่านั้นได้อย่างไร

> diff d1/*.cpp d2/*.cpp

ดูเหมือนจะไม่ทำงาน (ด้วยเหตุผลที่ชัดเจน)

[อาจเป็นเรื่องง่ายที่จะแก้ปัญหาด้วยลูป แต่ฉันพยายามหาวิธีที่หรูหรากว่า]

คำตอบ:


13

คุณสามารถใช้เชลล์ลูปที่ทำงานต่างกันสำหรับแต่ละไฟล์ แต่จะไม่ตรวจจับกรณีที่ d2 มีไฟล์ แต่ d1 ไม่ได้ มันอาจจะเพียงพอ

for file in d1/*.cpp; do
    diff "$file" "d2/${file##*/}"
done

หรือทั้งหมดในบรรทัดเดียว:

for file in d1/*.cpp; do diff "$file" "d2/${file##*/}"; done

${file##*/}ส่วนหนึ่งคือการขยายตัวพารามิเตอร์พิเศษ

หากตัวแปรไฟล์มีอยู่d1/hello.cppแล้ว"${file##*/}"จะขยายไปยังhello.cpp(มูลค่าของไฟล์ แต่ด้วยทุกอย่างจนถึงและรวมถึงการสุดท้าย / ลบออก)

ดังนั้น"d2/${file##*/}"จะส่งผลให้d2/hello.cppและคำสั่ง diff ผลลัพธ์จึงเป็นdiff d1/hello.cpp d2/hello.cpp

ดูhttp://mywiki.wooledge.org/BashFAQ/100สำหรับข้อมูลเพิ่มเติมเกี่ยวกับการจัดการสตริงใน bash

ในบันทึกด้านข้างระบบควบคุมเวอร์ชัน (เช่นการโค่นล้ม git Mercurial ฯลฯ ... ) จะทำให้การกระจายประเภทนี้ง่ายขึ้นมาก


ฉันคิดว่าทั้งสองคำตอบที่ดีนี้ตรงไปตรงมาเมื่อมีหลายประเภทไฟล์ (แม้ว่าฉันพูดถึงในคำถามที่ฉันกำลังมองหาวิธีแก้ปัญหาไม่ลูป) ดังนั้นฉันยอมรับมัน การเพิ่มที่เพิ่มเข้ามานั้นอยู่echo "${file##*/}";ก่อนdiffคำสั่งดังนั้นอย่างใดอย่างหนึ่งจึงรู้ว่าไฟล์ใดที่ถูกเปรียบเทียบจริง นอกจากนี้ตามที่ระบุไว้ในคำตอบของ @ Rinzwind วิธีนี้ไม่ครอบคลุมกรณีที่รายการไฟล์ไม่เหมือนกันในทั้งสองไดเรกทอรี
ysap

52

diff -qr {DIR1} {DIR2} ทำทุกไฟล์ในทั้งสองไดเรกทอรี

  • q แสดงความแตกต่างเท่านั้น
  • rไม่เกิดซ้ำ ปล่อยทิ้งไว้หากคุณไม่ต้องการ

คุณไม่สามารถบอกdiffให้ใช้สัญลักษณ์แทนได้โดยตรง แต่คุณสามารถเพิ่ม:

-x PAT  --exclude=PAT
    Exclude files that match PAT.

-X FILE    --exclude-from=FILE
   Exclude files that match any pattern in FILE.

เพื่อแยกไฟล์ ดังนั้นหากคุณต้องการ*.cppวิธีที่ง่ายที่สุดคือการสร้างไฟล์ข้อความที่แสดงรายการไฟล์ทั้งหมดที่ไม่ได้*.cppเป็น คุณสามารถทำสิ่งนี้ได้ด้วยคำสั่งต่อไปนี้: ls -I "*.cpp" > excluded_filesโดยที่-I "*.cpp"อาร์กิวเมนต์นั้นข้ามไฟล์. cpp ทั้งหมด โปรดทราบว่าจำเป็นต้องมีเครื่องหมายอัญประกาศ


เรียบง่ายและทำงานได้อย่างไร้ที่ติ
Jose Gómez

4

บางเวลาหลังจากถามคำถามฉันพบmeldยูทิลิตี diff และใช้มันตั้งแต่นั้นมา นี่เป็นโปรแกรมที่ใช้ GUI ที่ยอดเยี่ยมซึ่งทำให้การเปรียบเทียบและผสานระหว่างไฟล์และไดเรกทอรีเป็นงานที่ง่ายมาก มันเปรียบเทียบสองหรือสามทาง

โดยเฉพาะมันตอบคำถามเดิมของฉันว่าจะแสดงการเปรียบเทียบรหัสเนื้อหาของไดเรกทอรีและให้คุณเปรียบเทียบไฟล์ที่ต้องการด้วยการดับเบิลคลิกที่ชื่อไฟล์

หากต้องการมากกว่าการเปรียบเทียบสามทางแล้วgvimdiff(ตามตัวvimแก้ไข) ก็ดีเช่นกันที่ให้ฟังก์ชั่นนี้


1

มีวิธีแก้ปัญหาที่มีน้ำหนักเบาสำหรับที่:

  1. ตั้งค่าปลั๊กอินเล็ก ๆ นี้http://www.vim.org/scripts/script.php?script_id=5309
  2. ทำdiff dir1 dir2 | vim -R -ที่เปลือกหอย

มันจะเพิ่มการพับและการเปรียบเทียบแบบเคียงข้างกันสำหรับไฟล์ที่ถูกเปลี่ยน

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.