将xargs用于并行Python脚本

时间:2016-09-26 23:08:42

标签: python bash parallel-processing xargs

我目前有一个bash脚本script.sh,有两个嵌套循环。第一个枚举a的可能值,第二个枚举b的可能值,如

#!/bin/sh
for a in {1..10}
do
    for b in {1..10}
    do
        nohup python script.py $a $b &
    done
done

因此,这会产生100个运行script.py的Python进程,每个进程对应一个(a,b)对。但是,我的机器只有5个内核,所以我想将进程数限制为5,以避免颠簸/浪费切换。目标是我总是运行5个进程,直到完成所有100个进程。

xargs似乎是这样做的一种方法,但我不知道如何将这些参数传递给xargs。我已经检查了其他类似的问题,但是不能理解周围的bash行话,以便知道发生了什么。例如,我试过

seq 1 | xargs -i --max-procs=5 bash script.sh

但这似乎没有做任何事情 - script.sh像以前一样运行,仍然会产生100个进程。

我认为我误解了xargs是如何工作的。

谢谢!

3 个答案:

答案 0 :(得分:4)

这实际上看起来更像是:

#!/bin/bash
for a in {1..10}; do
  for b in {1..10}; do
    printf '%s\0' "$a" "$b"
  done
done | xargs -0 -x -n 2 -P 5 python script.py

请注意,没有nohup,也没有任何& - 跟踪并发调用的数量,xargs需要直接执行Python脚本,而且该进程不能退出直到它完成。

非标准(但可广泛使用)-0扩展名要求输入采用NUL分隔格式(使用printf '%s\0'创建);这确保了具有空格,引号,反斜杠等参数的正确行为。

同样非标准-P 5设置最大进程数(比--max-procs=5稍微更便携,GNU支持但不支持现代BSD xargs。)

-n 2表示Python脚本的每个实例只接收两个参数,因此每对输入开始一个。

-x(与-n 2一起使用)表示如果单个Python实例不能给出两个参数(例如,如果参数太长以至于两者都不适合在单个命令行上),这应该被视为失败,而不是仅使用一个参数调用Python实例。

答案 1 :(得分:1)

如果您使用bash,则以下内容应该有效:

#!/bin/bash

for a in {1..10}
do
    for b in {1..10}
    do
        if [ `jobs | wc -l` -lt 6 ]; then # less than 6 background jobs
            nohup python script.py $a $b &
        else
            wait -n   # wait for any background job to terminate
        fi
    done
done

答案 2 :(得分:1)

GNU Parallel适用于这些类型的工作:

parallel python script.py ::: {1..10} ::: {1..10}

如果您需要以不同的方式放置$ a和$ b,可以使用{1}和{2}来引用这两个输入源:

parallel python script.py --option-a {1} --option-b {2} ::: {1..10} ::: {1..10}

GNU Parallel是一个通用的并行程序,可以很容易地在同一台机器上或在你有ssh访问权限的多台机器上并行运行作业。它通常可以替换for循环。

如果要在4个CPU上运行32个不同的作业,并行化的直接方法是在每个CPU上运行8个作业:

Simple scheduling

GNU Parallel会在完成后生成一个新进程 - 保持CPU处于活动状态,从而节省时间:

GNU Parallel scheduling

<强>安装

如果没有为您的发行版打包GNU Parallel,您可以进行个人安装,不需要root访问权限。这可以在10秒内完成:

(wget -O - pi.dk/3 || curl pi.dk/3/ || fetch -o - http://pi.dk/3) | bash

有关其他安装选项,请参阅http://git.savannah.gnu.org/cgit/parallel.git/tree/README

了解详情

查看更多示例:http://www.gnu.org/software/parallel/man.html

观看介绍视频:https://www.youtube.com/playlist?list=PL284C9FF2488BC6D1

完成教程:http://www.gnu.org/software/parallel/parallel_tutorial.html

注册电子邮件列表以获得支持:https://lists.gnu.org/mailman/listinfo/parallel