Script fails with spaces in directory names

前端 未结 1 1905
一整个雨季
一整个雨季 2021-01-16 11:12

I have a really easy question, I have found a bunch of similar questions answered but none that solved this for me.

I have a shell script that goes through a directo

相关标签:
1条回答
  • 2021-01-16 11:53

    Warning: Two of the three code samples below use bashisms. Please take care to use the correct one if you need POSIX sh rather than bash.


    Don't do any of those things. If your real problem does involve using find, you can use it like so:

    shopt -s nullglob
    while IFS='' read -r -d '' dir; do
      files=( "$dir"/* )
      printf '%s\t%s\n' "${#files[@]}" "$dir"
    done < <(find . -mindepth 1 -maxdepth 1 -type d -print0)
    

    However, for iterating over only immediate subdirectories, you don't need find at all:

    shopt -s nullglob
    for dir in */; do
      files=( "$dir"/* )
      printf '%s\t%s\n' "${#files[@]}" "$dir"
    done
    

    If you're trying to do this in a way compatible with POSIX sh, you can try the following:

    for dir in */; do
      [ "$dir" = "*/" ] && continue
      set -- "$dir"/*
      [ "$#" -eq 1 ] && [ "$1" = "$dir/*" ] && continue
      printf '%s\t%s\n' "$#" "$dir"
    done
    

    You shouldn't ever use ls in scripts: http://mywiki.wooledge.org/ParsingLs

    You shouldn't ever use for to read lines: http://mywiki.wooledge.org/DontReadLinesWithFor

    Use arrays and globs when counting files to do this safely, robustly, and without external commands: http://mywiki.wooledge.org/BashFAQ/004

    Always NUL-terminate file lists coming out of find -- otherwise, filenames containing newlines (yes, they're legal in UNIX!) can cause a single name to be read as multiple files, or (in some find versions and usages) your "filename" to not match the real file's name. http://mywiki.wooledge.org/UsingFind

    0 讨论(0)
提交回复
热议问题