rm -rf 所有文件和所有不带 . & .. 错误

Jak*_*son 114 wildcards rm

rm -rf /some/path/* 删除该目录(和子目录)中的所有非隐藏文件。

rm -rf /some/path/.* 删除该目录(但不是子目录)中的所有隐藏文件,并给出以下错误/警告:

rm: cannot remove directory: `/some/dir/.'
rm: cannot remove directory: `/some/dir/..'
Run Code Online (Sandbox Code Playgroud)

在目标目录中递归删除所有隐藏和非隐藏文件和文件夹而不收到关于.and的警告/错误的正确方法是什么..

Gil*_*il' 116

*匹配所有非点文件,.[!.]*匹配除.和 名称以 开头的文件之外的所有点文件..,并..?*匹配除... 它们一起匹配除.和之外的所有文件..。如果这三个模式中的任何一个都不匹配,它就会扩展到自己;rm -f不关心不存在的参数,所以这无关紧要。

rm -rf ..?* .[!.]* *
Run Code Online (Sandbox Code Playgroud)

您也可以使用find. 这更复杂,但即使有太多文件,上面的通配符会扩展到超出系统命令行长度限制,它也有工作的优势。

find . -name . -o -prune -exec rm -rf -- {} +
Run Code Online (Sandbox Code Playgroud)

您可能会发现删除并重新创建目录更清晰。即使另一个程序同时在原始目录中创建文件,这也具有导致空目录的优点(或缺点,视情况而定)。

  • 这应该是公认的答案,因为它可以防止父遍历和可能的删除。 (13认同)
  • @haylem 在 zsh 中,当启用历史替换时,您需要编写 `.[^.]*` 而不是 `.[!.]*`(默认情况下是交互情况,但不是在脚本中),因为 zsh 解析 ` !` 作为历史参考。但是在 zsh 中,您首先不需要它,您可以使用 `*(D)` 在通配符匹配中包含点文件(没有 `.` 或 `..`)。 (2认同)
  • `rm -rf /path/to/subdirectory/{..?*,.[!.]*,*} 2>/dev/null` (2认同)

evi*_*oup 52

您可以随时将错误消息发送至 /dev/null

rm -rf /some/path/.* 2> /dev/null
Run Code Online (Sandbox Code Playgroud)

你也可以

rm -rf /some/path/
mkdir /some/path/
Run Code Online (Sandbox Code Playgroud)

...那么您首先就不必费心处理隐藏文件。

  • 不删除和重新创建目录会带来文件权限不正确的风险(在服务器环境中尤其重要)。谁可以自动创建具有与以前相同权限的文件夹? (32认同)
  • 删除目录并不总是可行的。在我的情况下,目录是一个 docker 卷,虽然我可以在卷内做任何我想做的事情,但我不能从容器内更改卷本身。 (5认同)
  • 但是如果我只想删除隐藏文件呢? (4认同)
  • @YoLudke您是绝对正确的,在许多情况下这无关紧要,但删除文件夹并重新创建在语义上并不等同于清空该文件夹;所以要小心这样做! (3认同)

小智 26

刚刚意识到这是大多数 Linux 发行版中最方便的方法:

ls -A1 | xargs rm -rf
Run Code Online (Sandbox Code Playgroud)

在哪里

-A= 列出 .之外的所有内容..

-1 = 将所有项目放在一行中

  • 如果任何文件名包含空格、换行符、引号或反斜杠,则它不起作用。 (8认同)
  • 我看到的缺点是:你需要'cd'进入目录才能做到这一点。 (4认同)

Ign*_*ams 22

要么更改dotglobshell的选项并使用*,要么使用类似find.

find somedir -mindepth 1 -delete
Run Code Online (Sandbox Code Playgroud)

  • 或者你可以简单地`rm -rf /some/dir` 然后在它的位置创建一个新的空目录。 (3认同)

Paw*_*żak 8

这应该像@Gilles 的回答一样工作,但更紧凑:

rm -rf {,.[!.],..?}*
Run Code Online (Sandbox Code Playgroud)

或者

rm -rf dir/to/files/{,.[!.],..?}*
Run Code Online (Sandbox Code Playgroud)

if为了安全起见,还应该在脚本中添加一个for 用法:

if [ -d "$DIR" ]; then
    rm -rf ${DIR}/{,.[!.],..?}*
fi
Run Code Online (Sandbox Code Playgroud)


wil*_*ill 5

我建议你尝试

了转向ON (隐藏文件)

  • dotglob

    shopt -s dotglob

了转向OFF

  • 未设置 dotglob

    shopt -u dotglob

这种方法恰好担任我希望一个副本唯一缺少的隐藏目录命令。

    shopt -s    dotglob
    cp    -rvn  ./$from/*  ./$too/
    shopt -u    dotglob
Run Code Online (Sandbox Code Playgroud)

所以我做了一个删除(删除),哎呀......

    shopt -s    dotglob
    rm -fr ../message_splitter--044a/*
    shopt -u    dotglob
Run Code Online (Sandbox Code Playgroud)

……这也行!

我突然想到亲爱的读者看不到message_splitter目录。无论如何,它都有一个.svn需要删除的文件夹,并复制到其中。

man页面...

dotglob 如果设置,bash 将包含以“.”开头的文件名 在路径名扩展的结果中。

参考:


Kus*_*nda 5

在目标目录中递归删除所有隐藏和非隐藏文件和文件夹而不收到有关 . 和 ..?

假设有问题的目录是./dir,那么

rm -rf ./dir
Run Code Online (Sandbox Code Playgroud)

将递归地删除 中的所有文件./dir,包括隐藏文件和目录,并包括./dir目录本身。

如果您不想删除目录本身,那么您可以稍后重新创建它,或者使用

find ./dir -mindepth 1 -delete
Run Code Online (Sandbox Code Playgroud)

或者如果您find不支持-delete

find ./dir -mindepth 1 -depth -exec rm -rf {} ';'
Run Code Online (Sandbox Code Playgroud)

使用-mindepth 1允许您保留顶级目录./dir