Module java.base
Package java.lang

Class Process

java.lang.Object
java.lang.Process

public abstract class Process extends Object
Process提供了对由ProcessBuilder.start和Runtime.exec启动的本机进程的控制。该类提供了执行来自进程的输入、执行输出到进程、等待进程完成、检查进程的退出状态以及销毁(杀死)进程的方法。ProcessBuilder.start()Runtime.exec方法创建一个本机进程并返回Process的子类的实例,该实例可用于控制进程并获取有关其的信息。

创建进程的方法可能无法很好地处理某些本机平台上的特殊进程,例如本机窗口进程、守护进程、Microsoft Windows上的Win16/DOS进程或shell脚本。

默认情况下,创建的进程没有自己的终端或控制台。所有标准I/O(即stdin、stdout、stderr)操作将被重定向到父进程,可以通过使用方法getOutputStream()getInputStream()getErrorStream()获取的流来访问这些操作。字符和行的I/O流可以使用方法outputWriter()outputWriter(Charset)inputReader()inputReader(Charset)errorReader()errorReader(Charset)进行写入和读取。父进程使用这些流来向进程提供输入并获取输出。由于某些本机平台仅为标准输入和输出流提供有限的缓冲区大小,因此未能及时写入进程的输入流或读取进程的输出流可能导致进程阻塞,甚至死锁。

如有需要,也可以使用ProcessBuilder类的方法重定向进程I/O

当没有对Process对象的更多引用时,进程不会被终止,而是继续异步执行。

不要求由Process对象表示的进程异步或并发地与拥有Process对象的Java进程执行。

从1.5开始,ProcessBuilder.start()是创建Process的首选方式。

Process的子类应重写onExit()toHandle()方法,以提供一个完全功能的Process,包括进程ID有关进程的信息直接子级进程的直接子级加上这些子级的后代。通常,委托给底层Process或ProcessHandle是最简单且最有效的方法。

自:
1.0
  • Constructor Details

    • Process

      public Process()
      Process的默认构造函数。
  • Method Details

    • getOutputStream

      public abstract OutputStream getOutputStream()
      返回连接到进程正常输入的输出流。将流输出到由此Process对象表示的进程的标准输入中。

      如果进程的标准输入已使用ProcessBuilder.redirectInput重定向,则此方法将返回一个空输出流

      API注释:
      在同时写入getOutputStream()outputWriter()outputWriter(Charset)之前,应调用BufferedWriter.flush
      实现注释:
      实现注释:返回的输出流最好是缓冲的。
      返回:
      连接到进程正常输入的输出流
    • getInputStream

      public abstract InputStream getInputStream()
      返回连接到进程正常输出的输入流。该流从由此Process对象表示的进程的标准输出中获取数据。

      如果进程的标准输出已使用ProcessBuilder.redirectOutput重定向,则此方法将返回一个空输入流

      否则,如果进程的标准错误已使用ProcessBuilder.redirectErrorProcessBuilder.redirectErrorStream重定向,则此方法返回的输入流将接收进程的合并标准输出和标准错误。

      API注释:
      使用getInputStream()inputReader()时要非常小心。BufferedReader可能已经缓冲了来自输入流的输入。
      实现注释:
      实现注释:返回的输入流最好是缓冲的。
      返回:
      连接到进程正常输出的输入流
    • getErrorStream

      public abstract InputStream getErrorStream()
      返回连接到进程错误输出的输入流。该流从由此Process对象表示的进程的错误输出中获取数据。

      如果进程的标准错误已使用ProcessBuilder.redirectErrorProcessBuilder.redirectErrorStream重定向,则此方法将返回一个空输入流

      API注释:
      使用getErrorStream()errorReader()时要非常小心。BufferedReader可能已经缓冲了来自错误流的输入。
      实现注释:
      实现注释:返回的输入流最好是缓冲的。
      返回:
      连接到进程错误输出的输入流
    • inputReader

      public final BufferedReader inputReader()
      返回连接到进程标准输出的BufferedReader。使用本机编码的Charset读取标准输出的字符、行或流行。

      此方法委托给使用由native.encoding系统属性命名的CharsetinputReader(Charset)。如果native.encoding不是有效的字符集名称或不受支持,则使用Charset.defaultCharset()

      返回:
      使用native.encoding(如果支持)连接的BufferedReader,否则使用Charset.defaultCharset()
      自:
      17
    • inputReader

      public final BufferedReader inputReader(Charset charset)
      返回一个连接到此进程标准输出的BufferedReader,使用指定的字符集。这个BufferedReader可用于读取标准输出的字符、行或流行。

      字符通过从此进程的getInputStream()读取和解码字节的InputStreamReader读取。字节使用指定的charset解码为字符;对于错误输入和不可映射字符序列,将使用charset的默认替换。 BufferedReader从InputStreamReader读取和缓冲字符。

      第一次调用此方法会创建一个BufferedReader,如果再次使用相同的charset调用,则会返回相同的BufferedReader。再次使用不同的charset调用此方法是错误的。

      如果进程的标准输出已经使用ProcessBuilder.redirectOutput重定向,则InputStreamReader将从一个空输入流读取。

      否则,如果进程的标准错误已经使用ProcessBuilder.redirectErrorStream重定向,则此方法返回的输入读取器将接收进程的合并标准输出和标准错误。

      API 注意:
      同时使用getInputStream()inputReader(Charset)具有不可预测的行为,因为缓冲读取器会提前从输入流中读取。

      当进程终止且标准输入未被重定向时,从底层流中可用的字节的读取是尽力而为的,可能是不可预测的。

      参数:
      charset - 用于将字节解码为字符的Charset
      返回:
      使用charset连接到进程标准输出的BufferedReader
      抛出:
      NullPointerException - 如果charsetnull
      IllegalStateException - 如果多次使用不同的charset参数调用
      自:
      17
    • errorReader

      public final BufferedReader errorReader()
      返回一个连接到进程标准错误的BufferedReader,使用本机编码的Charset读取标准错误的字符、行或流行。

      此方法委托给使用由native.encoding系统属性命名的CharseterrorReader(Charset)。如果native.encoding不是有效的字符集名称或不受支持,则使用Charset.defaultCharset()

      返回:
      使用支持的native.encodingBufferedReader,否则使用Charset.defaultCharset()
      自:
      17
    • errorReader

      public final BufferedReader errorReader(Charset charset)
      返回一个连接到此进程标准错误的BufferedReader,使用指定的字符集。这个BufferedReader可用于读取标准错误的字符、行或流行。

      字符通过从此进程的getErrorStream()读取和解码字节的InputStreamReader读取。字节使用指定的charset解码为字符;对于错误输入和不可映射字符序列,将使用charset的默认替换。 BufferedReader从InputStreamReader读取和缓冲字符。

      第一次调用此方法会创建一个BufferedReader,如果再次使用相同的charset调用,则会返回相同的BufferedReader。再次使用不同的charset调用此方法是错误的。

      如果进程的标准错误已经使用ProcessBuilder.redirectErrorProcessBuilder.redirectErrorStream重定向,则InputStreamReader将从一个空输入流读取。

      API 注意:
      同时使用getErrorStream()errorReader(Charset)具有不可预测的行为,因为缓冲读取器会提前从错误流中读取。

      当进程终止且标准错误未被重定向时,从底层流中可用的字节的读取是尽力而为的,可能是不可预测的。

      参数:
      charset - 用于将字节解码为字符的Charset
      返回:
      使用charset连接到进程标准错误的BufferedReader
      抛出:
      NullPointerException - 如果charsetnull
      IllegalStateException - 如果多次使用不同的charset参数调用
      自:
      17
    • outputWriter

      public final BufferedWriter outputWriter()
      返回一个连接到进程标准输入的使用本机编码的BufferedWriter。将文本写入字符输出流,缓冲字符以提供对单个字符、数组和字符串的高效写入。

      此方法委托给使用由native.encoding系统属性命名的CharsetoutputWriter(Charset)。如果native.encoding不是有效的字符集名称或不受支持,则使用Charset.defaultCharset()

      返回:
      使用native.encoding系统属性的字符集连接到进程标准输入的BufferedWriter
      自:
      17
    • outputWriter

      public final BufferedWriter outputWriter(Charset charset)
      返回一个连接到进程标准输入的使用指定字符集的BufferedWriter。将文本写入字符输出流,缓冲字符以提供对单个字符、数组和字符串的高效写入。

      写入的字符由OutputStreamWriter编码为字节,并使用Charset写入此Process表示的进程的标准输入。对于错误输入和不可映射字符序列,将使用charset的默认替换。

      第一次调用此方法会创建一个BufferedWriter,如果再次使用相同的charset调用,则会返回相同的BufferedWriter。再次使用不同的charset调用此方法是错误的。

      如果进程的标准输入已经使用ProcessBuilder.redirectInput重定向,则OutputStreamWriter将写入一个空输出流

      API 注意:
      BufferedWriter写入字符、字符数组和字符串。将BufferedWriterPrintWriter结合使用可提供对基本类型和对象的高效缓冲和格式化,以及对换行符自动刷新的支持。调用BufferedWriter.flush()方法将缓冲的输出刷新到进程。

      在同时写入getOutputStream()outputWriter()outputWriter(Charset)时,应在写入OutputStream之前调用BufferedWriter.flush

      参数:
      charset - 用于将字符编码为字节的Charset
      返回:
      使用charset连接到进程标准输入的BufferedWriter
      抛出:
      NullPointerException - 如果charsetnull
      IllegalStateException - 如果多次使用不同的charset参数调用
      自:
      17
    • waitFor

      public abstract int waitFor() throws InterruptedException
      使当前线程等待,直到由此Process对象表示的进程终止。如果进程已经终止,则此方法立即返回。如果进程尚未终止,则调用线程将被阻塞,直到进程退出。
      返回:
      由此Process对象表示的进程的退出值。按照惯例,值0表示正常终止。
      抛出:
      InterruptedException - 如果当前线程在等待时被另一个线程中断,则等待将结束并抛出InterruptedException
    • waitFor

      public boolean waitFor(long timeout, TimeUnit unit) throws InterruptedException
      使当前线程等待,直到表示此Process对象的进程终止,或经过指定的等待时间为止。

      如果进程已经终止,则此方法立即返回值true。如果进程尚未终止且超时值小于或等于零,则此方法将立即返回值false

      此方法的默认实现轮询exitValue以检查进程是否已终止。强烈建议此类的具体实现重写此方法,以提供更高效的实现。

      参数:
      timeout - 最长等待时间
      unit - timeout参数的时间单位
      返回:
      如果进程已退出,则返回true;如果等待时间在进程退出之前已过,则返回false
      抛出:
      InterruptedException - 如果当前线程在等待时被中断。
      NullPointerException - 如果单位为null
      自版本:
      1.8
    • exitValue

      public abstract int exitValue()
      返回进程的退出值。
      返回:
      表示此Process对象的进程的退出值。按照惯例,值0表示正常终止。
      抛出:
      IllegalThreadStateException - 如果表示此Process对象的进程尚未终止
    • destroy

      public abstract void destroy()
      终止进程。由此Process对象表示的进程是否支持正常终止取决于实现。强制进程销毁被定义为立即终止进程,而正常终止允许进程干净地关闭。如果进程不活动,则不执行任何操作。

      当进程终止时,onExit()返回的CompletableFuture将被完成

    • destroyForcibly

      public Process destroyForcibly()
      强制终止进程。由此Process对象表示的进程将被强制终止。强制进程销毁被定义为立即终止进程,而正常终止允许进程干净地关闭。如果进程不活动,则不执行任何操作。

      当进程终止时,onExit()返回的CompletableFuture将被完成

      在由ProcessBuilder.start()Runtime.exec(java.lang.String)返回的Process对象上调用此方法将强制终止进程。

      API注释:
      进程可能不会立即终止。即在调用destroyForcibly()后,isAlive()可能会在短暂时间内返回true。如果需要,可以将此方法链接到waitFor()
      实现要求:
      此方法的默认实现调用destroy(),因此可能不会强制终止进程。
      实现说明:
      强烈建议此类的具体实现重写此方法,以提供符合规范的实现。
      返回:
      表示被强制销毁的进程的Process对象
      自版本:
      1.8
    • supportsNormalTermination

      public boolean supportsNormalTermination()
      如果destroy()的实现是正常终止进程,则返回true;如果destroy的实现强制并立即终止进程,则返回false

      在由ProcessBuilder.start()Runtime.exec(java.lang.String)返回的Process对象上调用此方法,根据平台实现返回truefalse

      实现要求:
      此实现抛出一个UnsupportedOperationException实例,并不执行其他操作。
      返回:
      如果destroy()的实现是正常终止进程,则返回true;否则,destroy()将强制终止进程
      抛出:
      UnsupportedOperationException - 如果Process实现不支持此操作
      自版本:
      9
    • isAlive

      public boolean isAlive()
      检查由此Process表示的进程是否仍在运行。
      返回:
      如果由此Process对象表示的进程尚未终止,则返回true
      自版本:
      1.8
    • pid

      public long pid()
      返回进程的本机进程ID。本机进程ID是操作系统分配给进程的标识号。
      实现要求:
      此方法的实现将进程ID作为toHandle().pid()返回。
      返回:
      进程的本机进程ID
      抛出:
      UnsupportedOperationException - 如果Process实现不支持此操作
      自版本:
      9
    • onExit

      public CompletableFuture<Process> onExit()
      返回一个用于处理进程终止的CompletableFuture<Process>CompletableFuture提供了在进程终止时触发依赖函数或操作的能力,这些函数或操作可以同步或异步运行。当进程终止时,无论进程的退出状态如何,CompletableFuture都将完成

      调用onExit().get()会等待进程终止并返回进程。该future可用于检查进程是否完成等待进程终止。取消CompletableFuture不会影响进程。

      ProcessBuilder.start()返回的进程会覆盖默认实现,以提供一种有效的等待进程退出的机制。

      API注释:
      使用onExitwaitFor的一种替代方法,它既能实现额外的并发性,又能方便地访问进程的结果。可以使用Lambda表达式来评估进程执行的结果。如果在使用值之前需要执行其他处理,则onExit是一种方便的机制,可以释放当前线程,并仅在需要值时阻塞。
      例如,启动一个进程来比较两个文件并获取它们是否相同的布尔值:
         Process p = new ProcessBuilder("cmp", "f1", "f2").start();
          Future<Boolean> identical = p.onExit().thenApply(p1 -> p1.exitValue() == 0);
          ...
          if (identical.get()) { ... }
       
      ,在CompletableFuture完成和依赖操作被调用之前,可以观察到进程已终止。
      实现要求:
      此实现在单独的线程中重复执行waitFor(),直到成功返回。如果waitFor的执行被中断,线程的中断状态将被保留。

      waitFor()成功返回时,CompletableFuture完成,无论进程的退出状态如何。如果同时等待大量进程,此实现可能会消耗大量内存用于线程堆栈。

      外部实现应重写此方法并提供更高效的实现。例如,要委托给底层进程,可以执行以下操作:

      
          public CompletableFuture<Process> onExit() {
             return delegate.onExit().thenApply(p -> this);
          }
       
      返回:
      用于进程的新CompletableFuture<Process>
      自版本:
      9
    • toHandle

      public ProcessHandle toHandle()
      返回进程的ProcessHandle。由ProcessBuilder.start()Runtime.exec(java.lang.String)返回的Process对象实现toHandle,相当于ProcessHandle.of(pid),包括对SecurityManager和RuntimePermission("manageProcess")的检查。
      实现要求:
      此实现会抛出一个 UnsupportedOperationException 的实例,并不执行其他操作。子类应该重写此方法以提供进程的 ProcessHandle。除非被重写,pid()info()children()descendants() 这些方法会操作 ProcessHandle。
      返回:
      返回一个进程的 ProcessHandle
      抛出:
      UnsupportedOperationException - 如果进程实现不支持此操作
      SecurityException - 如果安装了安全管理器并且它拒绝 RuntimePermission("manageProcess")
      自 JDK 版本:
      9
    • info

      public ProcessHandle.Info info()
      返回有关进程的信息快照。

      如果可用,ProcessHandle.Info 实例具有访问器方法,返回有关进程的信息。

      实现要求:
      此实现将进程的信息返回为: toHandle().info()
      返回:
      有关进程的信息快照,始终非空
      抛出:
      UnsupportedOperationException - 如果进程实现不支持此操作
      自 JDK 版本:
      9
    • children

      public Stream<ProcessHandle> children()
      返回进程的直接子进程的快照。直接子进程的父进程是该进程。通常,一个 未运行 的进程没有子进程。

      请注意,进程是异步创建和终止的。不能保证进程是 运行 的。

      实现要求:
      此实现将直接子进程返回为: toHandle().children()
      返回:
      一个顺序的 ProcessHandles 流,表示该进程的直接子进程
      抛出:
      UnsupportedOperationException - 如果进程实现不支持此操作
      SecurityException - 如果安装了安全管理器并且它拒绝 RuntimePermission("manageProcess")
      自 JDK 版本:
      9
    • descendants

      public Stream<ProcessHandle> descendants()
      返回进程的后代的快照。进程的后代是该进程的子进程以及这些子进程的后代,递归地。通常,一个 未运行 的进程没有子进程。

      请注意,进程是异步创建和终止的。不能保证进程是 运行 的。

      实现要求:
      此实现将所有子进程返回为: toHandle().descendants()
      返回:
      一个顺序的 ProcessHandles 流,表示该进程的后代
      抛出:
      UnsupportedOperationException - 如果进程实现不支持此操作
      SecurityException - 如果安装了安全管理器并且它拒绝 RuntimePermission("manageProcess")
      自 JDK 版本:
      9