Unix의 For 루프: 하위 디렉터리에 파일 포함

Unix의 For 루프: 하위 디렉터리에 파일 포함

Unix의 간단한 for 루프는 다음과 같습니다.

for FILE in $BASE_WORK_DIR/*.pdf
   do
     echo $FILE
   done

.pdf그러면 BASE_WORK_DIR 디렉터리의 모든 파일이 에코됩니다 .

BASE_WORK_DIRPDF 파일도 포함하는 하위 디렉터리가 있으면 어떻게 되나요?

이 경우 모든 PDF 파일 BASE_WORK_DIR과 해당 하위 디렉터리를 가져오도록 for 루프를 어떻게 디자인할 수 있습니까 BASE_WORK_DIR?

답변1

표준적이고 표준적이며 신뢰할 수 있는 구문은 다음과 같습니다.

find . -type f -name '*.pdf' -exec sh -c '
  for f do
    something with "$f"
  done' sh {} +

sh(파일 목록이 큰 경우 여러 호출을 실행할 수 있습니다.)

의 경우 zsh다음과 같습니다.

for f (./**/*(.NDoN)) {
  something with "$f"
}

( 숨겨진 파일을 포함하여 .의 경우 -type f목록 을 정렬하지 말고 일치하는 파일이 없어도 불평하지 마십시오.) 그러나 액세스할 수 없는 디렉터리에 대한 오류 메시지는 표시되지 않습니다.DoNN

답변2

에서는 bash4디렉토리에 대한 심볼릭 링크를 따라야 하는 경우 다음을 활성화 globstar하고 사용할 수 있습니다 **.

shopt -s globstar
for file in "$base_work_dir"/**/*.pdf
do
  echo "$file"
done

sh그렇지 않으면 스크립트 에서 find아마도 가장 좋은 접근 방식은 다음과 같습니다.

IFS='
'
set -f
for file in $(find "$base_work_dir" -name *.pdf)
do
  echo "$file"
done

( globstar 와 같은 심볼릭 링크를 따르는 -L옵션이 추가됨)findbash

파일 이름에 개행 문자가 포함되어 있으면 문제가 발생한다는 점에 유의하세요.

답변3

find파일 이름의 줄 바꿈 문제를 해결하는 또 다른 솔루션 :

find "$BASE_WORK_DIR" -name '*.pdf' -print0 |
  while IFS= read -d '' -r file;do
    # your magic here
  done

경고 사항: 이는 Zsh 및 Bash에서만 작동합니다.

-print0findGNU와 같은 일부 구현에만 사용할 수 있습니다 find. -exec printf '%s\0' {} +귀하의 검색이 이를 지원하지 않는 경우 이를 사용하십시오.

관련 정보