zoukankan      html  css  js  c++  java
  • Android执行程序或脚本的方法

    Java中提供了两种方法来执行程序或脚本:
    (1) 使用Runtime的exec()方法
    (2) 使用ProcessBuilder的start()方法

    ProcessBuilder.start() 和 Runtime.exec() 方法都被用来创建一个操作系统进程(执行命令行操作),并返回 Process 子类的一个实例,该实例可用来控制进程状态并获得相关信息。 

    1.调用ProcessBuilder的构造函数后执行start():

    1 Process process = new ProcessBuilder("/system/bin/ping").redirectErrorStream(true).start();  
    2 OutputStream stdout = process.getOutputStream();  
    3 InputStream stdin = process.getInputStream();  
    4 BufferedReader reader = new BufferedReader(new InputStreamReader(stdin));  
    5 BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(stdout));  

    2.用Runtime.getRuntime().exec()方法执行:

    1 Process process = Runtime.getRuntime().exec("/system/bin/ping");  
    2 OutputStream stdout = process.getOutputStream();  
    3 InputStream stderr = process.getErrorStream();  
    4 InputStream stdin = process.getInputStream();  
    5 BufferedReader reader = new BufferedReader(new InputStreamReader(stdin));  
    6 BufferedReader err= new BufferedReader(new InputStreamReader(stderr));  
    7 BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(stdout));  

    使用ProcessBuilder,可以通过redirectErrorStream(true)将错误输出流转移到标准输出流中,这样使用一次process.getInputStreamReader()就能读出该进程的所有输出。

    而使用Runtime.getRuntime().exec()方法时,错误的输出流还需通过process.getErrorStream()来获得。

    waitFor方法

    ProcessBuilder.start() 和 Runtime.exec() 方法创建Process 子类的一个实例。 程序主进程会等待process一定的时间,但是时间很少,可能process根本无法完成工作就结束了。 因此,针对使用较长时间做工作的process,就需要调用waitFor方法。 该方法会引起当前Thread等待,直到process中断。 

    此方法返回的退出值的过程。按照惯例,0表示正常终止。

    下面是一个进程执行后销毁的类:

      1 import java.io.InputStream;  
      2 import java.io.OutputStream;  
      3   
      4 public class ProcessModel {  
      5   
      6     /** 
      7      * 通过Android底层实现进程关闭 
      8      * 
      9      * @param process 
     10      */  
     11     public static void killProcess(Process process) {  
     12         int pid = getProcessId(process.toString());  
     13         if (pid != 0) {  
     14             try {  
     15                 android.os.Process.killProcess(pid);  
     16             } catch (Exception e) {  
     17                 try {  
     18                     process.destroy();  
     19                 } catch (Exception ex) {  
     20                 }  
     21             }  
     22         }  
     23     }  
     24   
     25     /** 
     26      * 获取当前进程的ID 
     27      * 
     28      * @param str 
     29      * @return 
     30      */  
     31     public static int getProcessId(String str) {  
     32         try {  
     33             int i = str.indexOf("=") + 1;  
     34             int j = str.indexOf("]");  
     35             String cStr = str.substring(i, j).trim();  
     36             return Integer.parseInt(cStr);  
     37         } catch (Exception e) {  
     38             return 0;  
     39         }  
     40     }  
     41   
     42   
     43     /** 
     44      * 关闭进程的所有流 
     45      * 
     46      * @param process 
     47      */  
     48     public static void closeAllStream(Process process) {  
     49         try {  
     50             InputStream in = process.getInputStream();  
     51             if (in != null)  
     52                 in.close();  
     53         } catch (Exception e) {  
     54             e.printStackTrace();  
     55         }  
     56         try {  
     57             InputStream in = process.getErrorStream();  
     58             if (in != null)  
     59                 in.close();  
     60         } catch (Exception e) {  
     61             e.printStackTrace();  
     62         }  
     63         try {  
     64             OutputStream out = process.getOutputStream();  
     65             if (out != null)  
     66                 out.close();  
     67         } catch (Exception e) {  
     68             e.printStackTrace();  
     69         }  
     70     }  
     71   
     72     /** 
     73      * 销毁一个进程 
     74      * 
     75      * @param process 
     76      */  
     77     public static void processDestroy(Process process) {  
     78         if (process != null) {  
     79             try {  
     80                 if (process.exitValue() != 0) {  
     81                     closeAllStream(process);  
     82                     killProcess(process);  
     83                 }  
     84             } catch (IllegalThreadStateException e) {  
     85                 closeAllStream(process);  
     86                 killProcess(process);  
     87             }  
     88         }  
     89     }  
     90   
     91   
     92     /** 
     93      * 通过线程进行异步销毁 
     94      * 
     95      * @param process 
     96      */  
     97     public static void asyncProcessDestroy(final Process process) {  
     98         Thread thread = new Thread(new Runnable() {  
     99             @Override  
    100             public void run() {  
    101                 processDestroy(process);  
    102             }  
    103         });  
    104         thread.setDaemon(true);  
    105         thread.start();  
    106     }  
    107 }  

    为了防止主控程序被waitfor方法阻塞,需要自己新建线程来处理Process流

     1 Process p = Runtime.getRuntime().exec(cmd);  
     2   
     3 StreamGobbler errorGobbler = new StreamGobbler(p.getErrorStream(), "ERROR");              
     4         
     5       // kick off stderr  
     6       errorGobbler.start();  
     7         
     8       StreamGobbler outGobbler = new StreamGobbler(p.getInputStream(), "STDOUT");  
     9       // kick off stdout  
    10       outGobbler.start();   
    11   
    12 p.waitFor();  
     1   
     2 import java.io.BufferedReader;  
     3 import java.io.IOException;  
     4 import java.io.InputStream;  
     5 import java.io.InputStreamReader;  
     6 import java.io.OutputStream;  
     7 import java.io.PrintWriter;  
     8   
     9 import com.sdc.callmaxent.util.FileUtil;  
    10   
    11 /** 
    12  * 用于处理Runtime.getRuntime().exec产生的错误流及输出流 
    13  * @author shaojing 
    14  * 
    15  */  
    16 public class StreamGobbler extends Thread {  
    17     InputStream is;  
    18     String type;  
    19     OutputStream os;  
    20           
    21     StreamGobbler(InputStream is, String type) {  
    22         this(is, type, null);  
    23     }  
    24   
    25     StreamGobbler(InputStream is, String type, OutputStream redirect) {  
    26         this.is = is;  
    27         this.type = type;  
    28         this.os = redirect;  
    29     }  
    30       
    31     public void run() {  
    32         InputStreamReader isr = null;  
    33         BufferedReader br = null;  
    34         PrintWriter pw = null;  
    35         try {  
    36             if (os != null)  
    37                 pw = new PrintWriter(os);  
    38                   
    39             isr = new InputStreamReader(is);  
    40             br = new BufferedReader(isr);  
    41             String line=null;  
    42             while ( (line = br.readLine()) != null) {  
    43                 if (pw != null)  
    44                     pw.println(line);  
    45                 System.out.println(type + ">" + line);      
    46             }  
    47               
    48             if (pw != null)  
    49                 pw.flush();  
    50         } catch (IOException ioe) {  
    51             ioe.printStackTrace();    
    52         } finally{  
    53             FileUtil.close(pw);  
    54             FileUtil.close(br);  
    55             FileUtil.close(isr);  
    56         }  
    57     }  
    58 }   

    ProcessBuilder.start() 和 Runtime.exec() 方法都被用来创建一个操作系统进程(执行命令行操作),并返回 Process 子类的一个实例,该实例可用来控制进程状态并获得相关信息。 

     

     

  • 相关阅读:
    Pandas的高级操作
    Pandas的拼接操作
    Matplotlib基础使用
    股票分析案例
    Pandas处理缺失的数据
    Pandas的基础使用
    python前端之CSS基础--常用样式
    python前端之CSS介绍--选择器
    python实现网站用户名密码自动登录
    Python前端HTML介绍
  • 原文地址:https://www.cnblogs.com/l2rf/p/5866119.html
Copyright © 2011-2022 走看看