폴더 및 목록 파일을 반복합니다.

폴더 및 목록 파일을 반복합니다.

3개의 파일이 포함된 "sample"이라는 폴더가 있습니다. 샘플 폴더에서 이러한 파일을 읽고 컬을 사용하여 HTTP 사이트에 게시하는 쉘 스크립트를 작성하고 싶습니다.

폴더 안의 파일을 나열하기 위해 다음을 작성했습니다.

for dir in sample/*; do
        echo $dir;
        done

그러나 그것은 나에게 다음과 같은 결과를 제공합니다.

sample/log

sample/clk

sample/demo

그 안에 상위 폴더를 추가합니다. 내가 원하는 출력은 다음과 같습니다(상위 폴더 이름 없음).

log

clk

demo

어떻게 해야 하나요?

답변1

basename파일의 선행 경로를 제거 하려면 다음을 수행하십시오.

for file in sample/*; do
    echo "$(basename "$file")"
done

하지만 왜 안 됩니까?

( cd sample; ls )

답변2

쉘이 이를 지원한다고 가정하면 매개변수 확장을 사용할 수 있습니다.

for path in sample/*; do
    printf -- '%s\n' "${path##*/}"
done

또는 해당 디렉토리로 변경하여 거기에 목록을 작성할 수 있습니다.

답변3

이는 디렉토리로 수행하려는 작업에 따라 다릅니다.

디렉토리인지 확인하지 않고 단순히 이름을 인쇄하려면 ls를 사용할 수 있습니다.

ls -1 sample

필터를 사용할 수 있기 때문에 find가 더 좋습니다.

find sample -type d -maxdepth 1 -printf '%f\n'

파일에 대해 명령을 실행하려면 for 루프 대신 find를 사용해야 합니다.

find sample -type d -maxdepth 1 -exec basename {} \;

답변4

*nix 시스템은 파일 이름의 일부로 거의 모든 문자(공백, 개행, 쉼표, 파이프 기호 등 포함)를 허용하므로 쉘 스크립트에서 "ls" 명령의 출력을 구문 분석해서는 안 됩니다. 이것은 신뢰할 수 없습니다. 바라보다ls의 출력을 구문 분석하면 안되는 이유.

찾기를 사용하여 파일 목록을 만듭니다. Bash를 사용하는 경우 "find"의 출력을 배열에 삽입할 수 있습니다. 아래 예는 작동하지 않는 "curl" 명령을 사용하고 있다는 점에 유의하세요!

searchDir="sample/"
oldFiles=()
while IFS= read -r -d $'\0' foundFile; do
    oldFiles+=("$foundFile")
done < <(find "$searchDir" -maxdepth 1 -type f -print0 2> /dev/null)

if [[ ${#oldFiles[@]} -ne 0 ]]; then
    for file in "${oldFiles[@]}"; do
        curl -F ‘data=@"$file"’ UPLOAD_ADDRESS
    done
fi

관련 정보