Làm thế nào để phát hiện xem có tìm thấy hay không.


16

Có một phương tiện thành ngữ nào để phát hiện xem "find" có tìm thấy kết quả khớp nào không? Tôi hiện đang sử dụng

COUNT=`find ... | wc -l`
if [ "$COUNT" -gt 0 ]; then

nhưng điều này có vẻ hơi gián tiếp với tôi Ngoài ra, tôi muốn tìm cách ngừng tìm kiếm một khi nó tìm thấy một trận đấu, vì vậy nó không lãng phí thời gian và công sức. Tôi chỉ cần biết liệu có bất kỳ tập tin phù hợp hay không.

Cập nhật: Tôi đã phạm sai lầm khi viết câu hỏi của mình mà không có mã trước mặt: Tôi sử dụng wc -ltrong một trường hợp khác, trong đó tôi cần biết tổng số tệp tìm thấy. Trong trường hợp tôi chỉ kiểm tra xem có trận đấu nào không, tôi đã sử dụng if [ -z $(find …) ].

Câu trả lời:


17

Nếu bạn biết bạn có GNU find, hãy sử dụng -quit để làm cho nó dừng lại sau trận đấu đầu tiên.

Có thể, đường ống đầu ra của findvào head -n 1. Cách đó findsẽ chết vì một đường ống bị hỏng sau một vài trận đấu (khi nó được lấp đầy headbộ đệm đầu vào).

Dù bằng cách nào, bạn không cần wcphải kiểm tra xem một chuỗi có trống hay không, trình bao có thể tự thực hiện.

if [ -n "$(find … | head -n 1)" ]; then …

Thú vị ... Tôi nghĩ -nchỉ áp dụng cho các biến 'được xác định' ($ abc, $ xyz, v.v.), nhưng tôi cho rằng $ (...) là biến tạm thời 'được xác định' .. +1 ... (và tôi chỉ đọc gần đây rằng việc sử dụng -nlà rủi ro, trừ khi bạn chắc chắn rằng biến đó chưa được khai báo và 'không được sử dụng) ... nhưng một temp sẽ không có khả năng này ... tức là. chưa được khởi tạo so với sản phẩm nào
Peter.O

2
@fred: Ngược lại, -nkiểm tra xem một chuỗi có trống không, nó không liên quan gì đến các biến. Những gì bạn đã đọc có thể nói rằng việc sử dụng -nkhông kiểm tra xem một biến có được xác định hay không: -n "$foo"là sai nếu foođược xác định nhưng trống và hiển thị thông báo lỗi bên dưới set -u. [ -n "${foo+1}" ]đáng tin cậy kiểm tra xem có foođược đặt hay không, nhưng xử lý các biến rỗng và không đặt giống hệt nhau thường là một ý tưởng hay: [ -n "${foo:+1}" ]hoặc chỉ [ -n "$foo" ]khi bạn không lo lắng set -u.
Gilles 'SO- ngừng trở nên xấu xa'

Cảm ơn! Tôi không có -quitsẵn, nhưng đường ống để head -n 1hoạt động (như vậy head -c 1, nó dừng lại thậm chí sớm hơn, nhưng có lẽ với lợi ích không đáng kể). Ngoài ra, tôi đã phạm sai lầm khi viết câu hỏi của mình mà không có mã trước mặt: Tôi sử dụng wc -ltrong một trường hợp khác, trong đó tôi cần biết tổng số tệp tìm thấy. Trong trường hợp tôi chỉ kiểm tra xem có trận đấu nào không, tôi đã sử dụng if [ -z `find … ` ].
Chris Trang

6

Bạn có thể sử dụng -quithành động để dừng lại sau trận đấu đầu tiên. Bạn có thể muốn kết hợp điều đó với một hành động khác (như -print) hoặc bạn sẽ không thể biết liệu nó có tìm thấy gì không.

Ví dụ: find ... -print -quitsẽ in đường dẫn của tệp phù hợp đầu tiên và sau đó thoát. Hoặc, bạn có thể sử dụng -printf 1 -quitđể in 1 nếu có kết quả trùng khớp và không có gì nếu không có.

findTrạng thái thoát của phản ánh xem có lỗi trong khi tìm kiếm hay không và liệu nó có tìm thấy gì không, vì vậy bạn phải kiểm tra đầu ra của nó để xem có khớp không.


-quitlà một phần mở rộng GNU. Nó sẽ không hoạt động trên các hệ thống sử dụng các triển khai tìm kiếm khác (1), chẳng hạn như OS X, BSD và có lẽ hầu hết các Unice thương mại.
Warren Young

Cảm ơn, thật hữu ích khi biết trong trường hợp tôi đang sử dụng một hệ thống khác. Thật không may, cả muỗi và -printf đều không có sẵn trên máy của tôi (Mac OS X).
Chris Trang

4

Thoát 0 dễ dàng với tìm kiếm, thoát> 0 khó hơn vì điều đó thường chỉ xảy ra với một lỗi. Tuy nhiên chúng ta có thể làm cho nó xảy ra:

if find -type f -exec false {} +
then
  echo 'nothing found'
else
  echo 'something found'
fi

Lưu ý rằng giải pháp này hiệu quả hơn so với sử dụng một mạng con; thực thi false chắc chắn nhanh hơn thực thi ngay cả Dash:

$ cat alfa.sh bravo.sh charlie.sh delta.sh
find -name non-existing-file -exec false {} +
find -name existing-file -exec false {} +
[ "$(find -name non-existing-file)" ]
[ "$(find -name existing-file)" ]

$ strace dash alfa.sh | wc -l
807

$ strace dash bravo.sh | wc -l
1141

$ strace dash charlie.sh | wc -l
1184

$ strace dash delta.sh | wc -l
1194

0

Bạn có thể bọc nó vào điều kiện vỏ, ví dụ:

[ "$(find . ...)" '!=' '' ] && echo Found || echo Not found

...Điều kiện phù hợp của bạn ở đâu , ví dụ -name *.txt.

Một số ví dụ khác:

[ "$(find /etc -name hosts)" ] && echo True || echo False
[ ! -z "$(find /etc -name hosts)" ] && echo True || echo False
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.