AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • 主页
  • 系统&网络
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • 主页
  • 系统&网络
    • 最新
    • 热门
    • 标签
  • Ubuntu
    • 最新
    • 热门
    • 标签
  • Unix
    • 最新
    • 标签
  • DBA
    • 最新
    • 标签
  • Computer
    • 最新
    • 标签
  • Coding
    • 最新
    • 标签
主页 / server / 问题 / 127221
Accepted
Sanjay
Sanjay
Asked: 2010-03-30 01:19:40 +0800 CST2010-03-30 01:19:40 +0800 CST 2010-03-30 01:19:40 +0800 CST

在linux上删除大量文件会占用CPU

  • 772

我在我的 RHEL 服务器上生成了超过 50GB 的缓存文件(典型的文件大小为 200kb,因此没有文件很大)。当我尝试删除这些文件时,需要 8-10 个小时。

然而,更大的问题是系统负载在这 8 到 10 小时内达到临界值。无论如何,我可以在删除期间控制系统负载。

我尝试使用

nice -n19 rm -rf *

但这对系统负载没有帮助。

PS 我在superuser.com上问了同样的问题,但没有得到足够好的答案,所以在这里尝试。

linux files
  • 9 9 个回答
  • 5427 Views

9 个回答

  • Voted
  1. Best Answer
    Unreason
    2010-03-30T03:10:12+08:002010-03-30T03:10:12+08:00

    以下是各种操作和文件系统的一些基准供您参考。(当然,在一个繁忙的系统上,您会得到不同的结果,但希望这会让您对预期的结果有所了解)。

    如果我坐在你的椅子上,我会尝试获得该场景的基线基准:

    • 确定操作将在与其他所有东西隔离的裸硬件上花费多长时间(是的,即使在相当旧的硬件上也应该花费更少的 7-8 小时)。
    • 尝试添加通常以受控方式发生的其他操作,看看是什么让它运行这么长时间

    一些数字。

    在 5 年前的笔记本上, ext3安装了 rw,noatime,运行 top,仅此而已,使用 shell 脚本 create10kdirs.sh 创建 10k 目录

    #!/bin/bash
    for i in $(seq 10000)
    do
        mkdir $i
    done
    

    sudo time ./create10kdirs.sh
    24.59user
    20.70system
    0:47.04elapsed
    96%CPU (0avgtext+0avgdata 0maxresident)k80inputs+8outputs (1major+2735150minor)pagefaults 0swaps

    使用 sudo time rm -rf
    0.10user
    19.75system
    0:20.71elapsed
    95%CPU (0avgtext+0avgdata 0maxresident)k0inputs+8outputs (0major+222minor)pagefaults 0swaps删除 10k 个目录

    相同的硬件,ext4安装 rw,noatime 使用 shell 脚本创建 10k 目录 sudo time create10kdirs.sh
    23.96user
    22.31system
    0:49.26elapsed
    93%CPU (0avgtext+0avgdata0maxresident)k1896inputs+8outputs(20major+2715174minor)pagefaults 0swap

    使用 sudo time rm -rf
    0.13user
    16.96system
    0:28.21elapsed
    60%CPU (0avgtext+0avgdata0maxresident)k10160inputs+0outputs(1major+219minor)pagefaults0swaps删除 10k 个目录

    4 年旧笔记本,xfs安装 rw,relatime,USB 无障碍 sudo time create10kdirs.sh
    14.19user
    13.86system
    0:29.75elapsed
    94%CPU (0avgtext+0avgdata0maxresident)k432inputs+0outputs(1major+2735243minor)pagefaults 0swaps


    使用sudo time rm -rf
    0.13user
    2.65system
    0:08.20elapsed
    33%CPU (0avgtext+0avgdata 0maxresident)k120inputs+0outputs (1major+222minor)pagefaults 0swaps删除 10k 个目录

    结论:这个旧硬件将在大约 21 秒 * 40 = 12 分 40 秒内擦除 ext3 上的 400k 小文件+文件夹。在 xfs(没有障碍)上,它会在大约 5m20s 内完成。在这两个测试用例中,测试机器都没有承受重负载,但在我看来,您的问题似乎与您选择的文件系统并不严格相关。

    EDIT2 另外,在运行高于基准测试后,我尝试使用 find 删除。-mindepth 1 -maxdepth 1 -删除

    和结果!:

    ext3 使用 sudo time find 删除 10k 个目录。-mindepth 1 -maxdepth 1 -delete
    0.04user
    0.44system
    0:00.88elapsed
    55%CPU (0avgtext+0avgdata 0maxresident)k516inputs+8outputs(1major+688minor)pagefaults0swaps


    ext4 使用sudo time find删除 10k 个目录。-mindepth 1 -maxdepth 1 -delete
    0.05user
    0.66system
    0:01.02elapsed
    70%CPU (0avgtext+0avgdata 0maxresident)k568inputs+0outputs (1major+689minor)pagefaults交换

    xfs 使用
    sudo time find 删除 10k 目录。-mindepth 1 -maxdepth 1 -delete
    0.06user
    0.84system
    0:04.55elapsed
    19%CPU (0avgtext+0avgdata 0maxresident)k416inputs+0outputs (3major+685minor)pagefaults 0swaps

    真正的结论是 rm -rf 不是很聪明,而且它对于大树的性能不佳。(前提是我的测试用例真的很有代表性)。

    注意:我还测试了 xargs 变体,它很快,但没有上面的那么快。

    • 9
  2. CesarB
    2010-03-30T03:05:04+08:002010-03-30T03:05:04+08:00

    正如您在评论中提到的,您正在使用ext3.

    众所周知,rm在 ext3 上处理大文件的性能很差;这是固定的东西之一ext4。例如,请参阅这篇文章或kernelnewbies(其中提到范围提高了大文件的删除和截断速度)。

    我不知道这适用于您的典型文件大小。我希望它至少能应用一点,因为大约 200kB 你已经ext3在ext4.


    作为一种解决方法(因为您可能不会ext4为此升级),每次只删除几个文件并sleep在删除之间添加一个。它并不漂亮,但应该有助于减少负载。

    此外,如果在断电时丢失文件不是问题(因为它是某种缓存),您可以将它们放在一个单独的分区中,您可以mkfs在启动时再次使用该分区,并且在ext3没有日志甚至ext2. 高负载的原因可能是被刷新到磁盘的日志与读取冲突(您在另一篇文章中提到您有很多并发读取)。

    • 5
  3. Dom
    2010-03-30T02:04:05+08:002010-03-30T02:04:05+08:00

    也许外壳是问题的原因。您应该直接使用 find :find /dir -mindepth 1 -maxdepth 1 -delete

    • 3
  4. PP.
    2010-03-30T01:58:06+08:002010-03-30T01:58:06+08:00

    这可能相关,也可能不相关:但我曾遇到过rm无法处理我在命令行(通过星号运算符)提供的文件数量的情况。相反,我会使用 shell 中的以下命令:

    for i in *; do rm -rf $i; done
    

    在这种情况下,您可能会删除树,在这种情况下,上述可能无法满足您的需要。您可能必须将删除操作分成几部分,例如

    for i in [a-mA-M]*; do rm -rf $i; done
    for i in [n-zN-Z]*; do rm -rf $i; done
    
    • 2
  5. Chopper3
    2010-03-30T01:29:56+08:002010-03-30T01:29:56+08:00

    那只有 250,000 个左右的文件,应该不是问题——您使用的是什么文件系统,这个卷是否用于其他任何用途?

    • 1
  6. Michael Steinfeld
    2012-08-25T13:07:42+08:002012-08-25T13:07:42+08:00

    当您有很多像您描述的文件时,您每次都在调用该命令。此外,您还必须牢记日志 FS,您正在处理缓冲区命中和元数据,这会极大地影响处理时间。

    最好的办法是使用上面提到的 find 命令,只使用不太明显的功能。

    find / -name filename.* -exec /bin/rm -f '{}' \+
    

    基本上“+”是你的朋友。这样做是在集合中创建文件名,并在每个集合中调用一次 rm 命令。这与 'xargs' 所做的几乎相同,但如果在 BSD/Linux 上,您不必担心正确的标志。

    很好奇这对你来说能加速多少。因此,如果您还在,请回复。祝你好运 !

    • 1
  7. markus_b
    2010-03-30T04:25:59+08:002010-03-30T04:25:59+08:00

    在研究了文件系统基准后,我选择了 JFS 作为 mymytv 视频文件的文件存储,因为文件删除速度很快(而且 mytv 等待删除完成,使 IO 变得迟缓)。

    你也可以通过'find' 和'xargs' 来调用'rm' 而不是rm -rf。这可能会更快:

    find <dir> | xargs rm
    
    • 0
  8. Brian Showalter
    2010-03-31T06:23:40+08:002010-03-31T06:23:40+08:00

    如何将这些文件的列表通过管道传输到 Perl 并使用它的 unlink 函数?

    find <dir> | perl -nle 'unlink;'
    
    • 0
  9. sinping
    2010-03-31T06:28:19+08:002010-03-31T06:28:19+08:00

    我同意它不应该花那么长时间,但根据所使用的底层存储,密集读取可能是预期的。我认为最终你最好的解决方案是添加额外的磁盘并在它们之间拆分你的活动。如果您沿着这条路线走,RAID 在某些情况下可能会有所帮助。iostat 在这些时间告诉您什么?您还可以使用 for 循环并将 'rm' 命令包装在 'time' 中以获取一些附加信息。

    另一种可能性,当然取决于您的设置和应用程序,但也许您可以将这些缓存文件放在不同的分区上并定期格式化驱动器而不是删除文件?我认为运行 mkfs 会大大减少时间,但是当这种情况发生时您的应用程序将不可用,因此它并不理想。

    我也喜欢更频繁地清理它们的想法。在 cron 中说,你每小时安排一次这样的事情:

    find ./ -maxdepth 1 -type f -name "some pattern" -ctime +1 -exec rm -f {} \;

    这将删除所有超过 24 小时的文件,而不是尝试一次全部完成。

    • 0

相关问题

  • 你最喜欢的 Linux 发行版是什么?[关闭]

  • 更改 PHP 的默认配置设置?

  • 保护新的 Ubuntu 服务器 [关闭]

  • (软)Ubuntu 7.10 上的 RAID 6,我应该迁移到 8.10 吗?

  • 在 SQL Server 中,何时应将 PRIMARY Data FileGroup 拆分为辅助数据文件?

Sidebar

Stats

  • 问题 205573
  • 回答 270741
  • 最佳答案 135370
  • 用户 68524
  • 热门
  • 回答
  • Marko Smith

    新安装后 postgres 的默认超级用户用户名/密码是什么?

    • 5 个回答
  • Marko Smith

    SFTP 使用什么端口?

    • 6 个回答
  • Marko Smith

    从 IP 地址解析主机名

    • 8 个回答
  • Marko Smith

    如何按大小对 du -h 输出进行排序

    • 30 个回答
  • Marko Smith

    命令行列出 Windows Active Directory 组中的用户?

    • 9 个回答
  • Marko Smith

    什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同?

    • 3 个回答
  • Marko Smith

    如何确定bash变量是否为空?

    • 15 个回答
  • Martin Hope
    MikeN 在 Nginx 中,如何在维护子域的同时将所有 http 请求重写为 https? 2009-09-22 06:04:43 +0800 CST
  • Martin Hope
    Tom Feiner 如何按大小对 du -h 输出进行排序 2009-02-26 05:42:42 +0800 CST
  • Martin Hope
    0x89 bash中的双方括号和单方括号有什么区别? 2009-08-10 13:11:51 +0800 CST
  • Martin Hope
    Kyle Brandt IPv4 子网如何工作? 2009-08-05 06:05:31 +0800 CST
  • Martin Hope
    Noah Goodrich 什么是 Pem 文件,它与其他 OpenSSL 生成的密钥文件格式有何不同? 2009-05-19 18:24:42 +0800 CST
  • Martin Hope
    Brent 如何确定bash变量是否为空? 2009-05-13 09:54:48 +0800 CST
  • Martin Hope
    cletus 您如何找到在 Windows 中打开文件的进程? 2009-05-01 16:47:16 +0800 CST

热门标签

linux nginx windows networking ubuntu domain-name-system amazon-web-services active-directory apache-2.4 ssh

Explore

  • 主页
  • 问题
    • 最新
    • 热门
  • 标签
  • 帮助

Footer

AskOverflow.Dev

关于我们

  • 关于我们
  • 联系我们

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve