쉘을 더 잘 배우고 항상 xargs에 의존할 필요가 없도록 하기 위해 다른 방법을 찾으려고 노력해 왔습니다.
find . -name *.tcl | xargs -I{} cat {}
xargs를 사용하면 혼란스러운 느낌이 들며 이를 달성할 수 있는 여러 가지 방법이 있는지 궁금합니다.
편집: 다른 해결책은 다음을 사용하는 것입니다.
find . -name "*.tcl" | cat `cat /dev/stdin`
왜 파일 이름을 먼저 분류한 다음 문자열 대신 파일로 분류해야 하는지 이해가 안 됩니다...
답변1
하위 프로세스에서 find를 사용하고 출력을 cat에 공급할 수도 있습니다. :)
cat $(find . -name "*.tcl")
답변2
조회 시 exec를 사용할 수 있습니다.
find . -name "*.tcl" -exec cat {} \;
-exec
그 사이의 모든 것과 후행은 \;
실행할 명령입니다. xargs와 마찬가지로 찾기 결과를 {}로 바꿀 수 있습니다. 발견된 각 파일에 대해 cat이 실행됩니다(xargs가 STDIN을 통해 제공된 파일 목록을 반복하는 방식과 비슷함).
어떤 사람들은 파이프를 사용하지 않거나 다른 응용 프로그램을 시작하지 않기 때문에 이것이 더 효율적이라고 생각할 수도 있습니다.
답변3
을 사용하는 경우 bash
다음을 수행하세요.
shopt -s globstar # to match files recursively
cat -- **/*.tcl
답변4
단순화를 위해 제안된 깨끗하고 읽기 쉬운 솔루션을 선호합니다.마크 코말린스키. 그러나 Bash에서는 이를 수행하는 방법이 많이 있습니다. 또 다른 흥미로운 접근 방식은 리디렉션을 완전히 피하고 cat
리디렉션을 활용하는 것입니다.
find . -name '*.tcl' -exec sh -c 'printf "%s\n" "$(< {})' \;;
실제로 Bash 내장 기능만 사용하여 모든 작업을 수행하려면 다음과 같이 리디렉션을 사용할 수 있습니다.혼돈이 가져온 글로벌 솔루션:
shopt_globstar_temp="$(shopt -p globstar)";
shopt -s globstar;
for filename in **/*.bat; do
printf "%s" "$(< "${filename}")";
done;
${shopt_globstar_temp};
이것들은 약간 복잡하지만 여기서 나의 목적은 Bash가 할 수 있다는 것을 보여주는 것입니다.파일 설명자와 리디렉션의 몇 가지 강력한 기능. 주어진 문제에 대해 여러 가지 해결책이 있는 경우가 많습니다.
왜 파일 이름을 먼저 분류한 다음 문자열 대신 파일로 분류해야 하는지 이해가 안 됩니다...
의 출력은 cat /dev/fd/stdin
이전 예제와 동일하므로 해당 파일 목록으로 효과적으로 대체 find
되고 해당 파일 목록을 인수 목록으로 사용합니다.<filename1>.tcl <filename2>.tcl ...
cat
같은 예에서 cat을 사용해야 하는 이유가 궁금하다면 모든 프로그램이 인수를 같은 방식으로 처리하는 stdin
것은 아니기 때문입니다 . 을 통해 stdin
데이터를 전송하면 읽을 파일 이름으로 해석되지 않고 동일한 데이터가 단순히 출력됩니다.cat
stdin
cat