Java的多进程运行模式分析
一般我们在java中运行其它类中的方法时,无论是静态调用,还是动态调用,都是在当前的进程中执行的,也就是说,只有一个java虚拟机实例在运行。而有的时候,我们需要通过java代码启动多个java子进程。这样做虽然占用了一些系统资源,但会使程序更加稳定,因为新启动的程序是在不同的虚拟机进程中运行的,如果有一个进程发生异常,并不影响其它的子进程。
在Java中我们可以使用两种方法来实现这种要求。最简单的方法就是通过Runtime中的exec方法执行java classname。如果执行成功,这个方法返回一个Process对象,如果执行失败,将抛出一个IOException错误。下面让我们来看一个简单的例子。
// Test1.java文件import java.io.*;public class Test{ public static void main(String[] args) { FileOutputStream fOut = new FileOutputStream("c:\\Test1.txt"); fOut.close(); System.out.println("被调用成功!"); }}// Test_Exec.javapublic class Test_Exec{ public static void main(String[] args) { Runtime run = Runtime.getRuntime(); Process p = run.exec("java test1"); }} // Test_Exec_Out.javaimport java.io.*;public class Test_Exec_Out{ public static void main(String[] args) { Runtime run = Runtime.getRuntime(); Process p = run.exec("java test1"); BufferedInputStream in = new BufferedInputStream(p.getInputStream()); BufferedReader br = new BufferedReader(new InputStreamReader(in)); String s; while ((s = br.readLine()) != null) System.out.println(s); }} // Test2.java文件import java.io.*;public class Test{ public static void main(String[] args) { BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); System.out.println("由父进程输入的信息:" + br.readLine()); }}// Test_Exec_In.javaimport java.io.*;public class Test_Exec_In{ public static void main(String[] args) { Runtime run = Runtime.getRuntime(); Process p = run.exec("java test2"); BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(p.getOutputStream())); bw.write("向子进程输出信息"); bw.flush(); bw.close(); // 必须得关闭流,否则无法向子进程中输入信息 // System.in.read(); }} // Test_Exec_Out.javaimport java.io.*;public class Test_Exec_Out{ public static void main(String[] args) { ProcessBuilder pb = new ProcessBuilder("java", "test1"); Process p = pb.start(); … … }} ProcessBuilder pb = new ProcessBuilder("Command", "arg2", "arg2", ''');// 设置环境变量Map<String, String> env = pb.environment();env.put("key1", "value1");env.remove("key2");env.put("key2", env.get("key1") + "_test"); pb.directory("..\abcd"); // 设置工作目录Process p = pb.start(); // 建立子进程