我在我的 36 核服务器(EC2 c4.8xlarge/Amazon Linux)上运行这样的命令。
find . -type f | parallel -j 36 mycommand
需要处理的文件数量约为 1,000,000 个,需要数十分钟。它应该同时运行 36 个进程。但是从 的结果来看top
,最多只有 10 个进程,其中 70% 处于空闲状态。ps
显示更多进程,但其中大多数已停止运行。
我猜是因为每个进程mycommand
完成得太快,parallel
赶不上新进程的产生。所以我尝试
parallel --nice 20
给自己分配更多的 CPU 时间parallel
,但没有成功。
有人有想法改善这个问题吗?
$ parallel --version GNU parallel 20151022
答案1
需要处理的文件数量约为 1,000,000 个,需要几十分钟。
因此,您每秒运行大约 600 个作业。单个 GNU Parallel 作业的开销约为 2-5 毫秒,因此,当您每秒获得超过 200 个作业时,如果不进行调整,GNU Parallel 的性能将不会更好。
调整的目的是让更多的parallel
s 生成作业并行。从https://www.gnu.org/software/parallel/man.html#EXAMPLE:-Running-more-than-250-jobs-workaround
cat myinput | parallel --pipe -N 100 --round-robin -j50 parallel -j100 your_prg
这样,您将拥有 50 个 GNU Parallel,每个每秒可以产生 100 个作业。
答案2
呃,如果我理解你的问题,你想同时处理所有文件吗?
parallel
将启动的多个实例mycommand
,而不是多个find
实例。
答案3
您正在尝试打开一百万个文件,每次打开 36 个。即使您的命令可以在一个 CPU 上全速运行,您仍然需要首先打开这些文件。I/O 是计算机上最耗时的操作之一。最好的办法是预先将尽可能多的文件加载到机器的 RAM 中,并尽可能在 RAM 中工作。根据您的 RAM 大小,这可能会显著提高性能,因为一旦开始读取,如果一个接一个地立即进行后续读取,则后续读取往往会利用缓存。您可能还想确保您的文件系统以缓存高效的方式放置文件,并且当涉及多个后续读取时,它是一个好的文件系统。
我认为parallel
这次重构不会给你带来太大的帮助。