2009-05-22 3 views
100

매우 큰 파일 집합보다 효율적이며 어느 것을 사용해야합니까?find -exec cmd {} + vs | xargs

find . -exec cmd {} + 

또는

find . | xargs cmd 

(이 exec 달리, 가능한 몇 배 cmd을 실행

+0

관련 항목 : https://stackoverflow.com/questions/9612090/how-to-loop-through-file-names-returned-by-find –

답변

94

속도 차이는 중요하지 않습니다.

는하지만 당신은 확인해야한다 :

  1. 스크립트가 더 파일이 파일 이름 등 공백, 탭을 가지고하지 않을 것이라고 가정하지 않을 것이다; 첫 번째 버전은 안전하고, 두 번째 버전은 안전하지 않습니다.

  2. 스크립트는 "-"으로 시작하는 파일을 옵션으로 처리하지 않습니다.

    find . -exec cmd -option1 -option2 -- {} + 
    

    또는

    find . -print0 | xargs -0 cmd -option1 -option2 -- 
    

    첫 번째 버전은 당신이 일을 무시할 수로 쓰기 짧고 쉽게,하지만 두 번째 버전 :

그래서 코드는 다음과 같이한다 "-exec cmd {} +"은 GNU findutils의 비교적 새로운 옵션입니다 (2005 년 이래 많은 실행 시스템이 아직 없을 예정입니다). buggy recently. 또한 많은 사람들이 다른 답변에서 알 수 있듯이이 "-exec cmd {} +"을 모른다.

+4

-print0은 GNU 찾기 (및 GNU xargs) 옵션도 누락되었습니다 많은 비 Linux 시스템에서 발생하므로 이식성 주장은 유효하지 않습니다.그러나 -print를 사용하고 xargs를 -0으로두면 * 매우 유용합니다. – dannysauer

+4

요점은 -print0이 없으면 공백이나 탭 등이있는 파일이 있으면 작동하지 않는다는 것입니다. "foo -o index.html"과 같은 파일 이름이있는 것처럼 보안 취약점이 될 수 있습니다. 옵션으로 취급됩니다. 빈 디렉토리에서 "touch - foo \ -o \ index.html; find. | xargs cat"을 시도하십시오. "cat : invalid option - 'o'" – Tometzky

+2

그의 예제는 -가 들어있는 파일 이름입니다. -print0이 없으면 find는 ./foo -o index.html을 출력합니다. 어쩌면 -로 시작하는 것이 큰 문제는 아니지만 결과는 거의 변경되지 않으며 다중 사용자 시스템에서 스크립트가 세계에서 읽을 수있는 경우 공격 벡터를 제공 할 수 있습니다. – bobpaul

7
find . | xargs cmd 

이 더 효율적입니다 (더 이상한 문자가 파일 이름에이 없음을 가정) 매치마다 cmd 번씩 실행됩니다). 그러나 파일 이름에 공백이나 펑키 문자가 포함되어 있으면 문제가 발생합니다.

다음

이 사용하는 것이 좋습니다 :

find . -print0 | xargs -0 cmd 

이 파일 이름은 펑키 문자가 포함 된 경우에도 작동이 (-print0find 인쇄 NUL 종료 일치하게, -0xargs이 형식을 기대할 수 있습니다.)

+25

아니요 "찾을. -exec cmd {} \;" 그러나 "-exec cmd {} + 찾기". 후자는 한 번에 하나의 파일을 실행하지 않습니다. – Tometzky

+2

일치하는 파일이 없거나 각 파일에 대해'cmd'가별로 없다면'xargs' 방식은 실제로 상당히 느립니다. 예를 들어, 빈 디렉토리에서 실행될 때,'xargs' 버전은 최소한 두 번 걸릴 것입니다. 두 개의 프로세스가 단지 하나가 아니라 시작되어야하기 때문입니다. (예, 그 차이는 * nix에서 보통 감지 할 수 없지만 반복적으로 중요 할 수 있습니다. 또는 Windows에서 언젠가 시도해보십시오 ...) – SamB

관련 문제