我的目录中有一些文件和目录/var/foo/bar/baz
。现在,我想将它们全部移至/var/foo/bar
,并摆脱 baz。容易,对吧?
cd /var/foo/bar
mv baz/* .
rmdir baz
(为了讨论的目的,我忽略了以 . 开头的文件)
但!如果baz/
包含名为 的非目录文件怎么办baz
?我可以将其移动到其他地方,或者使用临时文件名,然后删除该目录baz
,然后将其移动到位。但这很乏味,而且命令也很多……还有另一种习惯的、更简单/更优雅的方法吗?
笔记:
- 如果存在其他名称冲突,
mv
则覆盖(并且可能提示)的正常语义是可以的。但对于baz
,它不会这样做,它只会失败。
答案1
cd /var/foo/bar/baz
for src in *; do
dest="${src}"
suffix=0
while [[ -e ../"${dest}" ]]; do
dest="${src}.${suffix}"
suffix=$((suffix+1))
done
mv -n "$src" ../"$dest"
done
cd ..
rmdir baz
一个相当简单的解决方案。准备将文件从当前目录移动到父目录,但如果已存在具有该名称的文件,请添加带有数字的后缀。但请确保不要使用以下数字还由于某种原因已经存在了。
如果任何被调用的东西存在,无论是目录、套接字、常规文件还是任何其他可能存在的东西, 该构造[[ -e file ]]
将返回 true。file
答案2
这太长了,但应该可以:
cd /var/foo/bar
bazbaz_tmp_file=$(mktemp baz/XXXXXXXXXXXXXX)
[[ -e baz/baz ]] && mv baz/baz $bazbaz_tmp_file
mv baz/* .
rmdir baz
mv $(basename $bazbaz_tmp_file) baz
注意:这假设我们可以安全地将任何其他文件从baz/
.