Câu hỏi Tìm thư mục chứa nhiều tệp cùng một tiện ích mở rộng


Tôi đang sử dụng Debian 8.0 và muốn tìm ví dụ để tìm các thư mục chứa nhiều hơn 1 .mkv tập tin. Tôi đã thử điều này và nó không thành công:

find -type d -exec find {} -name '*.mkv' | wc -l\;

Có một điểm tương tự Q & A ở đây trên SuperUsermà tôi không thể thích ứng. Điều này cũng không hiệu quả với tôi:

find . -maxdepth 1 -type d -exec bash -c "echo -ne '{} '; find '{}' -name '*.mkv' | wc -l" \; |   awk '$NF>=2'

Thông báo lỗi trỏ đến lỗi cú pháp:

bash: -c: line 0: syntax error near unexpected token `('

Lý do là thư mục có tên như sau:

Directory With Space and (Brackets)

1
2018-04-08 21:53


gốc


Tìm kiếm -exec dirname và chuyển hướng đầu ra đến một tập tin. Sử dụng sắp xếp và uniq để xem có bao nhiêu mkv trong mỗi thư mục. - ssnobody


Các câu trả lời:


Tôi khuyên bạn nên tìm cách tìm kiếm tất cả các tệp và in ra thư mục chứa của mỗi kết quả phù hợp, vì vậy bạn sẽ không cần lo lắng về việc phân tích các chuỗi lạ. Sau đó sử dụng uniq để đếm các bản sao và awk để lọc trên lĩnh vực đầu tiên in ra những người xảy ra nhiều hơn một lần. ví dụ.

find . -type f -iname '*.mkv' -printf '%h\n'|sort|uniq -c | awk '$1 > 1'

1
2018-04-08 22:18



Xuất sắc! Suy nghĩ đầu tiên của tôi là một cái gì đó như find -d -exec sh -c 'ls -d {}/*.mkv | wc -l' | …; giải pháp của bạn là thanh lịch hơn nhiều. Đề xuất: sử dụng uniq -cd và bạn có thể loại bỏ awk. - Scott
Hoạt động như được quảng cáo. Cần tra cứu, có vẻ rất hữu ích. - fswings


Tôi có thể thử một cái gì đó như thế này:

 find dirname -type f -name '*.mkv' -print0 | xargs -0 -L 1 dirname | sort | uniq -c | egrep -v '^ *1 ' | sed 's/^ *[0-9]* //'

Kết quả tìm ra tên của tất cả các tệp .mkv, sau đó xargs thực hiện một dirname trên mọi thứ để chỉ trích xuất tên thư mục, sắp xếp tất cả các entires, uniq cung cấp một số dòng lặp lại và sử dụng egrep loại bỏ những chỉ có 1 *. tập tin mkv và cuối cùng loại bỏ số lượng bằng cách sử dụng sed để cung cấp một danh sách các thư mục chỉ.

BTW, -print0 đang được sử dụng để tên tập tin ký tự đặc biệt không gây ra vấn đề xargs cần chuyển đổi -0 để giải thích đầu vào chính xác trong trường hợp đó .. Như đã lưu ý trong các chú thích, ngoại lệ là một ký tự dòng mới như một phần của tên tệp mà cá nhân tôi chưa gặp phải. xargs cần chuyển đổi -0 để giải thích đầu vào chính xác trong trường hợp đó.


2
2018-04-08 22:22



Điều này sẽ xử lý tên tệp có chứa các dòng mới, nhưng không phải là tên thư mục, bởi vì, nếu bạn có một tệp có tên đường dẫn là abc⏎def/foo.mkv Ở đâu ⏎ đại diện cho một dòng mới), sau đó dirname sẽ xuất abc⏎def, nên sort sẽ thấy hai dòng độc lập: abc và def. - Scott
Điểm lấy .... tuy nhiên tôi nghĩ rằng dòng mới sẽ rất hiếm. - mdpc
Tôi đồng ý; nhưng quan điểm của tôi là: tại sao làm cho một điểm xử lý đầu vào bệnh lý nếu bạn không xử lý tất cả? Ít nhất, đó là câu hỏi tiết lộ: đoạn cuối cùng của bạn có thể dẫn người đọc vào một cảm giác an toàn sai lầm. - Scott
Thử nghiệm và hoạt động như quảng cáo. - fswings
Điều này hoạt động trên mac của tôi! Hãy nhớ thay thế "dirname" và ".mkv" bằng thư mục thích hợp để tìm kiếm và mở rộng tệp, tương ứng. - AndyP


Loại hack nhưng đó là những gì tôi sẽ làm:

for dir in $(find . -type d)
do
  if [ $(ls -l "$dir" | grep '\.mkv$' | wc -l) -ge 2 ]
  then
    echo "$dir"
  fi
done

Cách hoạt động:

  1. Tìm tất cả các thư mục con của thư mục hiện tại find . -type d và lặp lại chúng với mỗi thư mục được lưu trong biến dir
  2. Nếu thư mục chứa nhiều hơn 2 tệp mkv, hãy in nội dung của $dir

Cập nhật: Xấu của tôi, tôi quên mất hơn 2 một phần của câu hỏi của bạn. Điều này cần được khắc phục bằng cách sử dụng -ge thay vì -eq (ở trên đã được sửa)!


0
2018-04-08 22:11





Một giải pháp perl

perl -le 'use File::Find; find (sub {if(/\.mkv$/) {$d{$File::Find::dir}++}}, "."); END {for (sort keys %d) {print if $d{$_}>1}};'

Mã này tương tự với mã khác. Các cây tre (của thư mục hiện tại ".") Đang đếm thư mục bất cứ khi nào nó gặp một tập tin .mkv (được lưu trữ trong băm% d). Sau khi đi bộ, tất cả các thư mục có nhiều hơn 2 tệp được in ra.


0
2018-04-08 22:44



Bạn có thể vui lòng chỉnh sửa câu trả lời của bạn để giải thích tại sao mã này trả lời câu hỏi? Trong mọi trường hợp, OP hỏi về việc không tìm kiếm giải pháp perl. - DavidPostill♦
Chắc rồi, đã thêm. Tôi không thấy bất cứ điều gì trong OP hỏi về một find giải pháp đặc biệt. - BowlOfRed
Cảm ơn đề xuất của bạn. Tôi đang tìm cách khai thác một bộ công cụ Linux điển hình. Tôi đã tìm cách để tránh phải làm điều này trong python ví dụ. - fswings