이 명령을 실행하면 작동합니다.
find . -type f -print0 | xargs md5sum
그러면 각 파일의 md5sum이 인쇄됩니다.
그러나 다른 명령의 경우 모든 파일을 단일 명령 호출로 전달하는 것 같습니다. 예를 들어, 이 문제가 있는 것 같습니다 printf
. 다음과 같은 경고가 표시 echo
됩니다 printf
.
printf: warning: ignoring excess arguments, starting with ...
echo를 사용하면 예를 들어 다음 명령이 있는 경우 한 줄만 인쇄됩니다.
find . -type f -print0 | xargs -r0 echo GOT
발견된 모든 파일과 같은 줄에 "GOT"가 한 번만 인쇄된 것을 볼 수 있습니다.
echo도 내장되어 있기 때문일 것이라고 생각했지만 /bin/echo를 명시적으로 실행하면 동일한 동작이 발생합니다.
참고로 make 명령에서도 다음과 같은 문제가 발생했습니다.
$ echo "a b c" | xargs echo GOT
GOT a b c
바꾸다:
GOT a
GOT b
GOT c
내가 뭘 잘못했나요? 먼저 명령에 접두사를 붙여 디버깅하는 것이 많은 도움이 되었지만 echo
그렇게 할 수도 없습니다.
편집: 댓글에서 언급했듯이 실제로 해당 -exec
옵션을 사용할 수 없습니다 find
. 실제로 정렬을 포함하는 다소 긴 파이프라인이 있지만 이는 관련 없는 세부 사항인 것 같고 내가 얻을 수 없다는 사실과는 아무런 관련이 없습니다. 더욱 간단한 파이프라인 작업.
답변1
표준 입력에서 가져온 모든 내용이 추가되고 일부 구분 기호로 구분된 xargs command-arg
명령의 단일 인스턴스를 실행하는 것으로 생각할 수 있습니다 (기본값은 예제에서 사용한 공백 또는 NUL 바이트입니다). command-arg
예를 들어:
echo 1 2 3 | xargs something
실행할 수 있습니다 something 1 2 3
. 또는 질문에 게시한 예를 사용하여:
echo "a b c" | xargs echo GOT
달리다 echo GOT a b c
.
표준 입력에서 얻은 각 인수 xargs를 사용하여 새 command-arg 인스턴스를 생성하려면 -n1 옵션을 사용할 수 있습니다.
$ echo "a b c" | xargs -n1 echo GOT
GOT a
GOT b
GOT c
물론 일부 명령은 여러 인수를 허용하지 않으므로 항상 사용해야 합니다 -n1
.
xargs 사용의 장점은 새 프로세스를 생성하는 것이 비용이 많이 드는 작업이므로 여러 인수를 사용하여 단일 프로세스를 실행하는 것이 더 빠르다는 것입니다. 이 답변에서 수행한 일부 벤치마크를 확인하십시오. https://unix.stackexchange.com/a/536023/72304
답변2
첫 번째 답변에서 언급한 "사용" 외에도 -n1
쉘에는 특정 명령의 내장 버전이 있을 수 있습니다. 명령이 다른 프로그램(예: )에서 호출되면 xargs
셸의 내장 버전이 아닌 외부 프로그램을 호출합니다.
특히 printf
Bash와 다른 여러 셸에 내장되어 있으며 Bash의 내장 버전은 모든 인수를 소진하는 데 필요한 만큼 형식을 반복합니다.
예를 들어 Bash의 내장 버전을 사용하면
printf '%s and %s\n' How now brown cow
2 줄을 출력하는 반면
/usr/bin/printf '%s and %s\n' How now brown cow
설치한 버전에 따라 매개변수가 너무 많다는 불만이 있을 수 있습니다.
답변3
일반적으로 나는 그것을 피할 것입니다 xargs
.
웹에서 찾은 대부분의 예제는 취약합니다. 환경이 코드를 작성하는 사람의 가정과 일치하지 않으면 예상치 못한 방식으로 중단될 것입니다.
이 질문에 제공된 예제에도 버그가 있습니다. find
...를 사용 -print0
하지만 다음을 사용합니다.xargs
아니요 -0
.
게다가 대부분의 용도는 xargs
불필요합니다. 특히 와 함께 사용할 경우 find
의 표현식을 사용하는 것이 더 안정적이고 오류가 발생할 가능성이 적습니다.-exec
find
주어진 예는 다음으로 대체될 수 있습니다.
find . -type f -exec md5sum {} +