찾기-실행 + 대 찾기 | xargs : 어느 것을 선택해야합니까?


32

의 동작을 모방 -exec하는 +옵션을 사용할 수 있음을 이해합니다 xargs. 한 양식을 다른 양식보다 선호하는 상황이 있습니까?

파이프 사용을 피하기 위해 개인적으로 첫 번째 양식을 선호하는 경향이 있습니다. 필자는 개발자가 find적절한 최적화를 수행 했음을 확신합니다. 나 맞아?

답변:


21

찾기 위해 전화를 연결하고 싶을 수도 있습니다 (한 번 배운 후에는 오늘 가능할 수도 있음). 물론 이것은 당신이 찾는 동안에 만 가능합니다. xargs로 파이프하면 범위를 벗어납니다.

작은 예, 두 개의 파일 a.lst 및 b.lst :

cat a.lst
fuddel.sh
fiddel.sh

cat b.lst
fuddel.sh

여기서 트릭은 없습니다. 단순히 "fuddel"을 포함하지만 하나만 "fiddel"을 포함한다는 사실입니다.

우리가 그것을 모른다고 가정하십시오. 두 가지 조건과 일치하는 파일을 검색합니다.

find -exec grep -q fuddel {} ";" -exec grep -q fiddel {} ";" -ls
192097    4 -rw-r--r--   1 stefan   stefan         20 Jun 27 17:05 ./a.lst

글쎄, grep이나 다른 프로그램이 두 문자열을 조건으로 전달하는 구문을 알고 있지만 그게 요점이 아닙니다. 파일을 인수로 지정하면 true 또는 false를 반환 할 수있는 모든 프로그램을 여기에서 사용할 수 있습니다. grep은 널리 사용되는 예입니다.

그리고 -ls 또는 -delete 와 같은 다른 찾기 명령으로 find -exec 를 따를 수도 있습니다 . delete는 rm (파일 제거)뿐만 아니라 rmdir (디렉토리 제거)도 수행합니다.

이러한 체인은 달리 지정되지 않는 한 (즉, -or스위치 (및 마스킹이 필요한 파엔)) 명령의 AND 조합으로 읽습니다 .

따라서 찾기 체인을 떠나지 않는 것이 편리합니다. -xargs를 사용할 때 어떤 이점도 얻지 못합니다. 파일을 전달할 때주의해야 할 필요가 없기 때문에 조심해야하므로 각 파일을 단일 인수로 전달하는 것이 자동으로 처리됩니다.

find {} 괄호에 대한 마스킹이 필요하다고 생각되면 증거를 요구하는 내 질문을 방문하십시오. 내 주장은 : 당신은하지 않습니다.


3
이 게시물은 새로운 사용 방법을 시인했습니다 find. 고마워요!
rahmu

1
"-xargs를 사용하는 데 이점이 없습니다". 4 개의 코어 중 3 개가 유휴 상태가되지 않도록하는 -exec방법은 무엇입니까 xargs -P4?
Damian Yerrick

1
@DamianYerrick : ";"에없는 -exec 명령 종료 그러나 + (/ 더하기 부호)가 있습니다.
사용자 알 수 없음

25

파일 이름을 안전하게 파이핑 xargs하려면 옵션을 find지원 하고 해당 옵션을 읽을 수있는 옵션 ( 또는 )이 있어야합니다 . 그렇지 않으면 이름에 인쇄 할 수없는 문자 나 백 슬래시 또는 따옴표 또는 공백이있는 파일 이름으로 인해 예기치 않은 동작이 발생할 수 있습니다. 반면에, 에 POSIX의 사양 은 휴대용 그래서, 그것은 안전 등에 관한 것입니다 , 그리고보다 확실히 안전합니다 . 내가 권하고 싶습니다 결코 일을하지 않고 .-print0xargs--null-0find -exec {} +findfind -print0 | xargs -0find | xargsfind | xargs-print0


6
이식성에 대한 주목할만한 예외 find … -exec … {} +는 OpenBSD인데,이 기능은 2012 년에 릴리스 된 5.1 버전에서만이 기능을 획득했습니다. 모든 BSD는 -print0수년 동안 OpenBSD를 포함 해 왔습니다. 당신이 얻을 수 있도록 솔라리스, 다른 한편으로는, POSIX에 스틱 기능을하지 -exec +아니하고 -print0.
Gilles 'SO- 악마 그만'

-print0고통스럽고 당신이 주장 할 수있는 xargs --delimiter "\n"것은 아니지만, 나는 후자를 발견 한 후에 결코 이전을 사용한 적이 없다.
Sridhar Sarnobat

3
나는 -0것보다 고통이 더 많은 것을 보지 못한다 --delimiter "\n".
jw013

2
또한 -0GNU xargs-r입력이 없으면 명령 실행을 피해야합니다.
Stéphane Chazelas

2
또 다른 문제는 | xargs -r0 cmd이다 cmd의 표준 입력이 (영향에 따라되어 xargs구현, 그건 /dev/null또는 관.
스테판 Chazelas가

10

-exec ... ;세미콜론을 피하는 것을 기억 하는 형식 을 사용하면 파일 이름 당 한 번 명령을 실행합니다. 을 사용 -print0 | xargs -0하면 파일 이름 당 여러 명령을 실행합니다. -exec +하나의 명령 줄에 여러 파일을 넣는 형식을 사용해야 하며 많은 수의 파일이 관련된 경우 훨씬 빠릅니다.

사용의 큰 장점 xargs 사용하여 병렬로 여러 개의 명령을 실행할 수있는 기능입니다 xargs -P. 멀티 코어 시스템에서는 시간을 크게 절약 할 수 있습니다.


6
당신은 -P대신에 의미 했습니다 -p. xargs -PPOSIX 표준이 아니라는 점 을 명심하십시오 find -exec {} +. 이는 이식성을 위해가는 경우 중요합니다.
jw013

@Alexios 더하기 부호를 피할 필요는 없습니다. 더하기 부호는 셸에 특별한 의미가 없기 때문에 제대로 find /tmp/ -exec ls "{}" +작동합니다.
다니엘 쿨만

1
물론입니다. 나는 -exec오랫동안 오랫동안 모든 것을 탈출 해왔다. (나는 masochist이다. 나는 따옴표를 사용하여 탈출 하지 않고 {}항상 입력하고 \{\}묻지 않는다) 모든 것이 지금 탈출 해야하는 것처럼 보인다.
Alexios

1
@Alexios : 중괄호 마스킹이 유용한 예제 (마조히스트 제외)를 발견하면 여기에 내 질문에 대한 답변 으로 제공 하십시오 . 나는 find /tmp/ -exec ls {} +작동하지 않는 예를 본 적이 없다 .
사용자가 알 수 없음

1
나를 위해, 이것은 SunOS 4 시절에 형성된 근육 기억입니다. 수년간 그것을 해왔 bash기 때문에 교정기를 그대로 받아 들일 때 완전히 알아 차리지 못했습니다 . 나는 중괄호가 탈출하지 않았다면 내가 사용한 오래된 껍질 중 적어도 하나가 히스에 적합하다고 확신합니다.
Alexios 2016 년

8

성능에 관해서 -exec … +는 모든 작업을 수행하는 단일 도구이기 때문에 더 좋을 것이라고 생각 했지만 GNU findutil의 문서-exec … + 중 일부는 효율성 이 떨어질 수 있다고 말합니다 .

[으로 찾기 -exec … +] 는 일부 용도보다 효율성이 떨어질 수 있습니다 xargs. 예를 들어 xargs, 이전 명령이 여전히 실행되는 동안 새 명령 행을 빌드 할 수 있으며 병렬로 실행할 여러 명령을 지정할 수 있습니다. 그러나이 find ... -exec ... +구성은 이식성이 뛰어나다는 장점이 있습니다. GNU findutils는 -exec ... +4.2.12 버전까지 ' '를 지원하지 않았습니다 [2005 년 1 월] ; 그 이유 중 하나는 이미 -print0어떤 경우에도 ' '조치 가 있었기 때문 입니다.

나는 그것이 무엇을 의미하는지 정확히 알지 못해서 derobert가 다음과 같이 채팅에서 물었 습니다.

find아마도 -exec … +실행중인 파일의 다음 배치를 계속 검색 할 수는 있지만 그렇지 않습니다.
find … | xargs …찾기는 다른 프로세스이므로 파이프 버퍼가 채워질 때까지 계속 실행됩니다.

(나에 의해 포맷)

거기에 있습니다. 그러나 성능이 실제로 중요한 경우 현실적인 벤치마킹을 수행하거나 그러한 경우에 쉘을 사용할 것인지 스스로에게 물어봐야합니다.

이 사이트에서 나는 사람들이 -exec … +양식을 더 단순하고 다른 답변에서 언급 한 이유 때문에 (예를 들어 생각하지 않고 이상한 파일 이름을 처리하기 때문에) 가능한 한 항상 사람들에게 조언하는 것이 좋습니다 .

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.