Linux进程管理器

来源:互联网 发布:儿童安全座椅 知乎 编辑:程序博客网 时间:2024/05/28 03:01

linux平台上,使用java语言编写的任务管理器
源码地址

工作原理

在子进程里执行linux的shell命令,获取输出流,从输出流中解析数据,从而得到进程信息,实现管理进程任务。

用到的知识点

java Process对象

Process类是一个抽象类(所有的方法均是抽象的),封装了一个进程(即一个执行程序)。
Process 类提供了执行从进程输入、执行输出到进程、等待进程完成、检查进程的退出状态以及销毁(杀掉)进程的方法。

Shell命令

要对进程进行监测和控制,首先必须要了解当前进程的情况,也就是需要查看当前进程,而 ps 命令就是最基本同时也是非常强大的进程查看命令。使用该命令可以确定有哪些进程正在运行和运行的状态、进程是否结束、进程有没有僵死、哪些进程占用了过多 的资源等等。总之大部分信息都是可以通过执行该命令得到的。
下面是本程序用到的Shell命令:
1、ps -aux –sort=-%cpu
(显示所有进程,按CPU占用率由高到低排序)
2、ps -aux
(显示所有进程)
3、kill -9 [PID]
(按PID来强制杀死进程)
(ps命令非常强大,感兴趣的朋友可以自行百度)

java Swing

用到的控件:
1. JTable
2. JButton
3. JTabbedPane
4. JPanel
5. JProgressBar

代码部分

ShellCmd类,用来保存所有使用到的Shell命令

package com.manager;/** * Shell命令枚举类 * Created by zf on 2017/4/6. */public enum ShellCmd {    SHOW_ALL_TASK("ps -aux --sort=-%cpu"),    SHOW_RUNNING_TASK("ps -aux"),    KILL_SELECT_TASK("kill -9 "),    SHOW_DYNAMIC_TREE("top");    private String cmd;    ShellCmd(String cmd) {        this.cmd = cmd;    }    public String getCmd() {        return cmd;    }}

ShellExec类,用于执行Shell命令

package com.manager;import com.dto.RawDataAnalyse;import java.io.*;import java.util.Vector;/** * Shell命令执行类 * Created by zf on 2017/4/6. */public class ShellExec {    private static boolean CLOSE_AFTER_EXEC = false;//执行完成后是否关闭终端    private static Vector<Vector<Object>> data = null;    private static ShellExec INSTANCE;    public static ShellExec getInstance() {        if (INSTANCE == null) {            INSTANCE = new ShellExec();        }        return INSTANCE;    }    public static Vector<Vector<Object>> getData() {        return data;    }    private ShellExec() {    }    public void showAllTask(boolean close_after_exec) {        CLOSE_AFTER_EXEC = close_after_exec;        Process pro = null;        try {            pro = Runtime.getRuntime().exec(ShellCmd.SHOW_ALL_TASK.getCmd());            BufferedReader br = new BufferedReader(new InputStreamReader(pro.getInputStream()));            RawDataAnalyse rawDataAnalyse = new RawDataAnalyse(br);            data = rawDataAnalyse.fromAllTaskCMD2Tasks();        } catch (Exception e) {            e.printStackTrace();        } finally {            if (CLOSE_AFTER_EXEC && pro != null && pro.isAlive()) {                pro.destroy();            }        }    }    public void showRunningTask(boolean close_after_exec) {        CLOSE_AFTER_EXEC = close_after_exec;        Process pro = null;        try {            pro = Runtime.getRuntime().exec(ShellCmd.SHOW_RUNNING_TASK.getCmd());            BufferedReader br = new BufferedReader(new InputStreamReader(pro.getInputStream()));            RawDataAnalyse rawDataAnalyse = new RawDataAnalyse(br);            data = rawDataAnalyse.fromRunningTaskCMD2Tasks();        } catch (IOException e) {            e.printStackTrace();        } finally {            if (CLOSE_AFTER_EXEC && pro != null && pro.isAlive()) {                pro.destroy();            }        }    }    public void showDynamicTree(boolean close_after_exec) {        CLOSE_AFTER_EXEC = close_after_exec;        Process pro = null;        try {            pro = Runtime.getRuntime().exec(ShellCmd.SHOW_DYNAMIC_TREE.getCmd());        } catch (IOException e) {            e.printStackTrace();        } finally {            if (CLOSE_AFTER_EXEC && pro != null && pro.isAlive()) {                pro.destroy();            }        }    }    public void kill(int PID, boolean close_after_exec) {        CLOSE_AFTER_EXEC = close_after_exec;        String cmd = ShellCmd.KILL_SELECT_TASK.getCmd() + PID;        Process pro = null;        try {            pro = Runtime.getRuntime().exec(cmd);        } catch (IOException e) {            e.printStackTrace();        } finally {            if (CLOSE_AFTER_EXEC && pro != null && pro.isAlive()) {                pro.destroy();            }        }    }}

RawDataAnalyse类,用于解析从输入流中读取到的原始数据

package com.dto;import java.io.BufferedReader;import java.io.IOException;import java.util.ArrayList;import java.util.List;import java.util.Vector;/** * 原始数据解析类 * 构造参数:带缓冲区的输入流br * Created by zf on 2017/4/7. */public class RawDataAnalyse {    private BufferedReader br = null;    public RawDataAnalyse(BufferedReader br) {        this.br = br;    }    /*    * 解析数据    * 数据来源:执行查看所有任务命令后得到的数据    * */    public Vector<Vector<Object>> fromAllTaskCMD2Tasks() {        Vector<Vector<Object>> result = new Vector<>();        String firstLine;        String line;        try {            firstLine = br.readLine();//剔除第一行            while ((line = br.readLine()) != null) {                String[] arr = line.split("\\s+");//按空格符来分割字符串                if (arr.length >= 11) {                    Task task = new Task();                    task.setUSER(arr[0]);                    task.setPID(Integer.parseInt(arr[1]));                    task.setCPU(Double.parseDouble(arr[2]));                    task.setMEM(Double.parseDouble(arr[3]));                    task.setVSZ(Integer.parseInt(arr[4]));                    task.setRSS(Integer.parseInt(arr[5]));                    task.setTTY(arr[6]);                    task.setSTAT(arr[7]);                    task.setSTART(arr[8]);                    task.setTIME(arr[9]);                    int num = arr.length;                    String command = "";                    for (int i = 10; i < num; i++) {                        command = command + arr[i].toString();                    }                    task.setCOMMAND(command);                    result.add(task.format2ArrayData());                } else {                    System.out.println("字符串分割出错!");                }            }        } catch (IOException e) {            e.printStackTrace();        }        return result;    }    public Vector<Vector<Object>> fromRunningTaskCMD2Tasks() {        Vector<Vector<Object>> result = new Vector<>();        String firstLine;        String line;        try {            firstLine = br.readLine();//剔除第一行            while ((line = br.readLine()) != null) {                String[] arr = line.split("\\s+");//按空格符来分割字符串                if (arr.length >= 11) {                    Task task = new Task();                    task.setUSER(arr[0]);                    task.setPID(Integer.parseInt(arr[1]));                    task.setCPU(Double.parseDouble(arr[2]));                    if (task.getCPU() != 0) {                        task.setMEM(Double.parseDouble(arr[3]));                        task.setVSZ(Integer.parseInt(arr[4]));                        task.setRSS(Integer.parseInt(arr[5]));                        task.setTTY(arr[6]);                        task.setSTAT(arr[7]);                        task.setSTART(arr[8]);                        task.setTIME(arr[9]);                        int num = arr.length;                        String command = "";                        for (int i = 10; i < num; i++) {                            command = command + arr[i].toString();                        }                        task.setCOMMAND(command);                        result.add(task.format2ArrayData());                    }                } else {                    System.out.println("字符串分割出错!");                }            }        } catch (IOException e) {            e.printStackTrace();        }        return result;    }}

Task类,进程对象类,用于实例化每一个进程

package com.dto;import java.util.Vector;/** * linux进程对象类 * 必须包含的属性:PID * Created by zf on 2017/4/7. */public class Task {    private int PID;//进程ID                 1    private String COMMAND;//实际指令        2    /*    * D 无法中断的休眠状态(通常 IO 的进程);    * R 正在运行可中在队列中可过行的;    * S 处于休眠状态;    * T 停止或被追踪;    * W 进入内存交换(从内核2.6开始无效);    * X 死掉的进程(从来没见过);    * Z 僵尸进程;    * */    private String STAT;//进程状态           3    private double CPU;//cup占用率           4    private double MEM;//物理内存占用率       5    private String USER;//用户名             6    private int VSZ;//虚拟内存使用量          7    private int RSS;//固定内存使用量          8    private String TTY;//关联的终端          9    private String START;//启动的时间        10    private String TIME;//占用CPU的时间      11    private Vector<Object> vector;    public String getUSER() {        return USER;    }    public void setUSER(String USER) {        this.USER = USER;    }    public int getPID() {        return PID;    }    public void setPID(int PID) {        this.PID = PID;    }    public double getCPU() {        return CPU;    }    public void setCPU(double CPU) {        this.CPU = CPU;    }    public double getMEM() {        return MEM;    }    public void setMEM(double MEM) {        this.MEM = MEM;    }    public int getVSZ() {        return VSZ;    }    public void setVSZ(int VSZ) {        this.VSZ = VSZ;    }    public int getRSS() {        return RSS;    }    public void setRSS(int RSS) {        this.RSS = RSS;    }    public String getTTY() {        return TTY;    }    public void setTTY(String TTY) {        this.TTY = TTY;    }    public String getSTART() {        return START;    }    public void setSTART(String START) {        this.START = START;    }    public String getTIME() {        return TIME;    }    public void setTIME(String TIME) {        this.TIME = TIME;    }    public String getCOMMAND() {        return COMMAND;    }    public void setCOMMAND(String COMMAND) {        this.COMMAND = COMMAND;    }    public String getSTAT() {        return STAT;    }    public void setSTAT(String STAT) {        this.STAT = STAT;    }    public Vector<Object> format2ArrayData() {        vector = new Vector<>();        vector.add(PID);        vector.add(COMMAND);        vector.add(STAT);        vector.add(CPU);        vector.add(MEM);        vector.add(USER);        vector.add(VSZ);        vector.add(RSS);        vector.add(TTY);        vector.add(START);        vector.add(TIME);        return vector;    }}

以上是关键代码,数据解析完成后,会放入TableModel,然后插入表控件中,显示给用户看。
————————————————————————————————————————————
简单的小程序,如果有什么好的的建议或者不懂的地方,欢迎留言。源码已开源到github上,地址在文章开头。
转载请注明出处

http://blog.csdn.net/zf1228

1 0