当 java 开始终端执行时已停用的进程
Defunct processes when java start terminal execution
我尝试用 kraken 对一些图像进行 ocr。我为此准备了一个控制台命令。
它很慢,所以我将它与 gnu parallel 结合起来。
find temp/ -name '*.tif' -or -name '*.jpg' | parallel -j4 kraken -i {} {}.html binarize segment ocr -h
当我在终端中执行此操作时,它工作正常。当我在 java(eclipse) 中启动它时,执行在 30 张图像后停止。它不会终止。它留下了不存在的进程。
String command = "find temp/ -name '*.tif' -or -name '*.jpg' | parallel -j4 kraken -i {} {}.html binarize segment ocr -h";
Process p = Runtime.getRuntime().exec(new String[]{"/bin/bash","-c",command});
p.waitFor() == 0;
我尝试了几种配置(更多内存(eclipse 和执行),更少线程),但没有任何帮助。
有人知道如何避免死进程或如何重新开始执行吗?
几乎可以肯定,问题是您没有使用进程的输出,导致其输出缓冲区已满,因此进程停滞。
尝试:
String command = "find temp/ -name '*.tif' -or -name '*.jpg' | parallel -j4 kraken -i {} {}.html binarize segment ocr -h";
Process p = Runtime.getRuntime().exec(new String[]{"/bin/bash","-c",command});
InputStream is = p.getInputStream();
// is.skip(Long.MAX_VALUE); Doesn't work
while (is.read() != -1) { } // consume all process output
p.waitFor();
完整的解决方案还将处理错误流。这可以通过启动一个单独的线程来完成,该线程 reads/skips 来自错误流的输入。
(或者,您可以在 bash 命令脚本中将输出重定向到 /dev/null
)。
我尝试用 kraken 对一些图像进行 ocr。我为此准备了一个控制台命令。 它很慢,所以我将它与 gnu parallel 结合起来。
find temp/ -name '*.tif' -or -name '*.jpg' | parallel -j4 kraken -i {} {}.html binarize segment ocr -h
当我在终端中执行此操作时,它工作正常。当我在 java(eclipse) 中启动它时,执行在 30 张图像后停止。它不会终止。它留下了不存在的进程。
String command = "find temp/ -name '*.tif' -or -name '*.jpg' | parallel -j4 kraken -i {} {}.html binarize segment ocr -h";
Process p = Runtime.getRuntime().exec(new String[]{"/bin/bash","-c",command});
p.waitFor() == 0;
我尝试了几种配置(更多内存(eclipse 和执行),更少线程),但没有任何帮助。
有人知道如何避免死进程或如何重新开始执行吗?
几乎可以肯定,问题是您没有使用进程的输出,导致其输出缓冲区已满,因此进程停滞。
尝试:
String command = "find temp/ -name '*.tif' -or -name '*.jpg' | parallel -j4 kraken -i {} {}.html binarize segment ocr -h";
Process p = Runtime.getRuntime().exec(new String[]{"/bin/bash","-c",command});
InputStream is = p.getInputStream();
// is.skip(Long.MAX_VALUE); Doesn't work
while (is.read() != -1) { } // consume all process output
p.waitFor();
完整的解决方案还将处理错误流。这可以通过启动一个单独的线程来完成,该线程 reads/skips 来自错误流的输入。
(或者,您可以在 bash 命令脚本中将输出重定向到 /dev/null
)。