`mvsomedir/*someotherdir`当somedir为空时
我正在编写一个自动 bash 脚本,将一些文件从一个目录移动到另一个目录,但第一个目录可能为空:
$ mv somedir/* someotherdir/
mv: cannot stat 'somedir/*': No such file or directory
如果目录为空,如何编写此命令而不产生错误?我应该只使用rmandcp吗?我可以先写一个条件检查来查看目录是否为空,但这感觉超重。
如果目录为空,我很惊讶命令会失败,所以我试图找出我是否缺少一些简单的解决方案。
环境:
- 猛击
- RHEL
回答
如果你真的想完全控制这个过程,它可能看起来像:
#!/usr/bin/env bash
# ^^^^- bash, not sh
restore_nullglob=$(shopt -p nullglob) # store the initial state of the nullglob setting
shopt -s nullglob # unconditionally enable nullglob
source_files=( somedir/* ) # store matching files in an array
if (( ${#source_files[@]} )); then # if that array isn't empty...
mv -- "${source_files[@]}" someotherdir/ # ...move the files it contains...
else # otherwise...
echo "No files to move; doing nothing" >&2 # ...write an error message.
fi
eval "$restore_nullglob" # restore nullglob to its original setting
解释运动部件:
- 当
nullglob设置,外壳膨胀*.txt,如果存在一个空列表中没有.txt文件; 否则(默认情况下),当没有匹配的文件时,它会扩展*.txt为字符串*.txt。 source_files是上面的一个数组——bash 存储列表的本机机制。${#source_files[@]}扩展到该数组的长度,而${source_files[@]}它自己扩展到它的内容。(( ))创建一个算术上下文,其中表达式被视为数学。在这种情况下,0 为假,正数为真。因此,if (( ${#source_files[@]} ))仅当数组中列出了多个文件时才为真source_files。
顺便说一句,请注意,nullglob在独立脚本中保存和恢复并不是必不可少的;展示如何执行此操作的目的是让您可以在较大的脚本中安全地使用此代码,这些脚本可能会假设是否nullglob已设置,而不会中断其他代码。