强制gnu-parallel将替换字符串视为命令

时间:2019-01-17 20:22:02

标签: gpu gnu-parallel

我想在使用替换字符串(例如:{%})时将包含命令列表的文件传递给gnu-parallel。

不幸的是,如果使用替换字符串,gnu-parallel会将文件中的命令解释为/bin/bash的参数。

这就是我想要做的:

parallel -j 8 'CUDA_VISIBLE_DEVICES=$(({%} - 1)) {}' < commands.txt

commands.txt的内容为:

/path/to/binary -arg1 a -arg2 1.0
/path/to/binary -arg1 a -arg2 1.1
...
/path/to/binary -arg1 z -arg2 9.9

但是,这会引发以下错误:

/bin/bash: /path/to/binary -arg1 a -arg2 1.0: command not found

我希望运行GNU Parallel:

CUDA_VISIBLE_DEVICES=0 /path/to/binary -arg1 a -arg2 1.0

环境变量CUDA_VISIBLE_DEVICES的目的是使每个进程在不同的GPU上运行(默认情况下,所有进程在同一GPU上运行)。如果我不需要CUDA_VISIBLE_DEVICES,则以下代码将完美运行:

parallel -j 8 < commands.txt

我该如何解决?

2 个答案:

答案 0 :(得分:1)

尽管--colsep有时可以工作,但这并不总是正确的选择。这将创建文件abcdef

echo 'touch abc\ def' | parallel -v --colsep ' ' A=B {}

通常最好使用eval取消对表达式的引用:

echo 'touch abc\ def' | parallel -v eval A=B {}

所以:

parallel -j 8 'eval CUDA_VISIBLE_DEVICES=$(({%} - 1)) {}' < commands.txt

如果您经常使用$(({%} - 1)),请考虑制作自己的替换字符串:

echo '--rpl {%-1}\ $_=slot()-1' >> ~/.parallel/config
parallel -j 8 'eval CUDA_VISIBLE_DEVICES={%-1} {}' < commands.txt

甚至:

echo '--rpl '"'"'{CUDA} $_="CUDA_VISIBLE_DEVICES=".(slot()-1)'"'" >> .parallel/config
parallel -j 8 'eval {CUDA} {}' < commands.txt

答案 1 :(得分:0)

使用$line可以达到目的:

--colsep ' '