GNU并行stderr,带有--files或可感知的--results树



我最近发现了GNU并行,它已经非常有用了,但我不知道如何将所有输出转换成任何可用的结构。以下是我的问题:

  • 我运行的命令需要几个小时或几天的时间,并且会产生大量到stdout和stderr的输出,所以我想重定向所有输出
  • 听起来--文件应该可以工作,对吧?但除非我疯了,否则我只能从这些文件中获取stdout。stderr只是用这个选项转储的吗
  • 好吧,结果怎么样?这可能要好一点,但有两个问题:
    1. 命令很长:/path/to/command-a--blah/path/to/data/ather/path{}。这使得一个荒谬的目录名和空格使得尝试做任何事情都很痛苦(例如"cat"find.name stdout"不起作用)
    2. stdout和stderr进入不同的文件,这通常是可以的,但在这种情况下,错误消息有时会在其他输出的中间产生,试图将它们重新组合在一起是一件痛苦的事情

那么:在并行中有没有任何方法,即不必修改我的命令,在使用--files时获取stderr,或者强制--results使用合理的目录名?

编辑:作为对评论的回应,我尝试了:

find controlFiles/ -name "*.txt" | parallel --files --tmpdir logs --tagstr {/.} -j15 --joblog logs/joblog --eta /path/to/command --opt --opt2 /path/to/data /path/to/output {} > logs/logfiles.txt

find controlFiles/ -name "*.txt" | parallel --files --results logs --tagstr {/.} -j15 --joblog logs/joblog --eta /path/to/command --opt --opt2 /path/to/data /path/to/output {} > logs/logfiles.txt

其中前者丢失stderr,而后者生成不可用的目录名

第2版:经过一系列的测试,我似乎不知何故进入了一种非常奇怪的状态。来自--results的目录结构本应以参数命名,但不知何故,我的目录结构使用了整个命令。当我尝试删除现有的日志目录并使用我认为相同的命令重新启动时,我得到了预期的行为。仍然不理想,但我当然可以接受。

最明显的解决方案是在作业完成后重命名目录的长部分。

cd resultdir/1/
rename 's:long/common/string/to/remove::' */2/*

另一个想法是使用新的.csv输出(从20161222开始提供):

parallel --results foo.csv ...

它将生成一个CSV文件,其中包含来自--joblog、参数、stdout和stderr的内容。如果你想在R或LibreCalc中进行后期处理,这会特别方便。

如果您喜欢混合的stderr/stdout,只需让2>&1成为你的命令的一部分:

parallel '(echo joe; ls /doesnotexists {}) 2>&1' ::: bar > foo

从版本20170122你可以:

parallel --results out/{/.} mycommand

最新更新