Java如何通过Process类从另一个类中调用目标类的main方法
问题排查及修复方案
存在的核心问题
- 流读取逻辑错误:使用
br.ready()判断是否可读会导致子进程还没完成输出时,读取逻辑直接提前终止,拿不到执行结果。 - 未捕获错误流:如果
Sumador执行报错,错误信息会输出到错误流中,当前代码只读取输入流,完全看不到报错信息,无法定位问题。 - 未等待子进程执行完成:主进程不会等待
Sumador进程跑完就会继续执行,可能出现主进程已经结束,子进程还没跑完的情况。 - 环境兼容性问题:直接执行
java Sumador.java是JDK 11新增的单文件运行特性,如果运行环境的JDK版本低于11,该命令会直接执行失败。 - 工作目录匹配问题:
ProcessBuilder默认工作目录为当前Lanzador进程的运行目录,如果Sumador.java不在该目录下,会出现找不到文件的错误。
修复后的代码
Lanzador类修改后内容
import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; public class Lanzador { public void lanzarSumador() { Process p; BufferedReader inputBr = null; BufferedReader errorBr = null; try { // 低版本JDK请先手动执行javac Sumador.java,然后将命令改为"java", "Sumador", "10", "20" ProcessBuilder pb = new ProcessBuilder("java", "Sumador.java", "10", "20"); // 如果Sumador.java不在当前工作目录,可以通过下面的方法指定路径,比如pb.directory(new File("d:/your/path/")); p = pb.start(); // 同时读取输入流和错误流 inputBr = new BufferedReader(new InputStreamReader(p.getInputStream())); errorBr = new BufferedReader(new InputStreamReader(p.getErrorStream())); // 等待子进程执行完成,获取退出码 int exitCode = p.waitFor(); System.out.println("Sumador进程退出码:" + exitCode); // 输出正常执行结果 String line; System.out.println("=====执行结果====="); while ((line = inputBr.readLine()) != null) { System.out.println(line); } // 输出错误信息 System.out.println("=====错误信息====="); while ((line = errorBr.readLine()) != null) { System.out.println(line); } } catch (IOException | InterruptedException e) { e.printStackTrace(); } finally { // 关闭流 try { if (inputBr != null) inputBr.close(); if (errorBr != null) errorBr.close(); } catch (IOException e) { e.printStackTrace(); } } } public static void main(String[] args) { Lanzador l = new Lanzador(); l.lanzarSumador(); } }
验证步骤
- 确认运行环境JDK版本:如果JDK版本<11,先执行
javac Sumador.java编译生成class文件,再将ProcessBuilder的命令修改为"java", "Sumador", "10", "20" - 确认
Sumador.java文件和Lanzador的运行工作目录一致,或者通过pb.directory()方法指定Sumador所在的目录 - 运行Lanzador即可看到输出结果:按照你的Sumador逻辑,输出结果应该是
Resultado: 145(10到19的累加和)
内容的提问来源于stack exchange,提问作者RubenMG
相关产品推荐
相关产品推荐

