首页 > 学院 > 开发设计 > 正文

一个简单的任务执行时间监视器 StopWatch

2019-11-08 00:44:06
字体:
来源:转载
供稿:网友

有时我们在做开发的时候需要记录每个任务执行时间,或者记录一段代码执行时间,最简单的方法就是打印当前时间与执行完时间的差值,然后这样如果执行大量测试的话就很麻烦,并且不直观,如果想对执行的时间做进一步控制,则需要在程序中很多地方修改,目前sPRing-framework提供了一个StopWatch类可以做类似任务执行时间控制,也就是封装了一个对开始时间,结束时间记录操作的java类,当然还有一些其他控制,代码如下:

/*  * Copyright 2002-2010 the original author or authors.  *  * Licensed under the Apache License, Version 2.0 (the "License");  * you may not use this file except in compliance with the License.  * You may obtain a copy of the License at  *  *      http://www.apache.org/licenses/LICENSE-2.0  *  * Unless required by applicable law or agreed to in writing, software  * distributed under the License is distributed on an "AS IS" BASIS,  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  * See the License for the specific language governing permissions and  * limitations under the License.  */    package com.test;    import java.text.NumberFormat;  import java.util.LinkedList;  import java.util.List;    /**  * Simple stop watch, allowing for timing of a number of tasks,  * exposing total running time and running time for each named task.  *  * <p>Conceals use of <code>System.currentTimeMillis()</code>, improving the  * readability of application code and reducing the likelihood of calculation errors.  *  * <p>Note that this object is not designed to be thread-safe and does not  * use synchronization.  *  * <p>This class is normally used to verify performance during proof-of-concepts  * and in development, rather than as part of production applications.  *  * @author Rod Johnson  * @author Juergen Hoeller  * @author Sam Brannen  * @since May 2, 2001  */  public class StopWatch {        /**      * Identifier of this stop watch.      * Handy when we have output from multiple stop watches      * and need to distinguish between them in log or console output.      */      private final String id;        private boolean keepTaskList = true;        private final List<TaskInfo> taskList = new LinkedList<TaskInfo>();        /** Start time of the current task */      private long startTimeMillis;        /** Is the stop watch currently running? */      private boolean running;        /** Name of the current task */      private String currentTaskName;        private TaskInfo lastTaskInfo;        private int taskCount;        /** Total running time */      private long totalTimeMillis;          /**      * Construct a new stop watch. Does not start any task.      */      public StopWatch() {          this.id = "";      }        /**      * Construct a new stop watch with the given id.      * Does not start any task.      * @param id identifier for this stop watch.      * Handy when we have output from multiple stop watches      * and need to distinguish between them.      */      public StopWatch(String id) {          this.id = id;      }          /**      * Determine whether the TaskInfo array is built over time. Set this to      * "false" when using a StopWatch for millions of intervals, or the task      * info structure will consume excessive memory. Default is "true".      */      public void setKeepTaskList(boolean keepTaskList) {          this.keepTaskList = keepTaskList;      }          /**      * Start an unnamed task. The results are undefined if {@link #stop()}      * or timing methods are called without invoking this method.      * @see #stop()      */      public void start() throws IllegalStateException {          start("");      }        /**      * Start a named task. The results are undefined if {@link #stop()}      * or timing methods are called without invoking this method.      * @param taskName the name of the task to start      * @see #stop()      */      public void start(String taskName) throws IllegalStateException {          if (this.running) {              throw new IllegalStateException("Can't start StopWatch: it's already running");          }          this.startTimeMillis = System.currentTimeMillis();          this.running = true;          this.currentTaskName = taskName;      }        /**      * Stop the current task. The results are undefined if timing      * methods are called without invoking at least one pair      * {@link #start()} / {@link #stop()} methods.      * @see #start()      */      public void stop() throws IllegalStateException {          if (!this.running) {              throw new IllegalStateException("Can't stop StopWatch: it's not running");          }          long lastTime = System.currentTimeMillis() - this.startTimeMillis;          this.totalTimeMillis += lastTime;          this.lastTaskInfo = new TaskInfo(this.currentTaskName, lastTime);          if (this.keepTaskList) {              this.taskList.add(lastTaskInfo);          }          ++this.taskCount;          this.running = false;          this.currentTaskName = null;      }        /**      * Return whether the stop watch is currently running.      */      public boolean isRunning() {          return this.running;      }          /**      * Return the time taken by the last task.      */      public long getLastTaskTimeMillis() throws IllegalStateException {          if (this.lastTaskInfo == null) {              throw new IllegalStateException("No tasks run: can't get last task interval");          }          return this.lastTaskInfo.getTimeMillis();      }        /**      * Return the name of the last task.      */      public String getLastTaskName() throws IllegalStateException {          if (this.lastTaskInfo == null) {              throw new IllegalStateException("No tasks run: can't get last task name");          }          return this.lastTaskInfo.getTaskName();      }        /**      * Return the last task as a TaskInfo object.      */      public TaskInfo getLastTaskInfo() throws IllegalStateException {          if (this.lastTaskInfo == null) {              throw new IllegalStateException("No tasks run: can't get last task info");          }          return this.lastTaskInfo;      }          /**      * Return the total time in milliseconds for all tasks.      */      public long getTotalTimeMillis() {          return this.totalTimeMillis;      }        /**      * Return the total time in seconds for all tasks.      */      public double getTotalTimeSeconds() {          return this.totalTimeMillis / 1000.0;      }        /**      * Return the number of tasks timed.      */      public int getTaskCount() {          return this.taskCount;      }        /**      * Return an array of the data for tasks performed.      */      public TaskInfo[] getTaskInfo() {          if (!this.keepTaskList) {              throw new UnsupportedOperationException("Task info is not being kept!");          }          return this.taskList.toArray(new TaskInfo[this.taskList.size()]);      }          /**      * Return a short description of the total running time.      */      public String shortSummary() {          return "StopWatch '" + this.id + "': running time (millis) = " + getTotalTimeMillis();      }        /**      * Return a string with a table describing all tasks performed.      * For custom reporting, call getTaskInfo() and use the task info directly.      */      public String prettyPrint() {          StringBuilder sb = new StringBuilder(shortSummary());          sb.append('/n');          if (!this.keepTaskList) {              sb.append("No task info kept");          } else {              sb.append("-----------------------------------------/n");              sb.append("ms     %     Task name/n");              sb.append("-----------------------------------------/n");              NumberFormat nf = NumberFormat.getNumberInstance();              nf.setMinimumIntegerDigits(5);              nf.setGroupingUsed(false);              NumberFormat pf = NumberFormat.getPercentInstance();              pf.setMinimumIntegerDigits(3);              pf.setGroupingUsed(false);              for (TaskInfo task : getTaskInfo()) {                  sb.append(nf.format(task.getTimeMillis())).append("  ");                  sb.append(pf.format(task.getTimeSeconds() / getTotalTimeSeconds())).append("  ");                  sb.append(task.getTaskName()).append("/n");              }          }          return sb.toString();      }        /**      * Return an informative string describing all tasks performed      * For custom reporting, call <code>getTaskInfo()</code> and use the task info directly.      */      @Override      public String toString() {          StringBuilder sb = new StringBuilder(shortSummary());          if (this.keepTaskList) {              for (TaskInfo task : getTaskInfo()) {                  sb.append("; [").append(task.getTaskName()).append("] took ").append(task.getTimeMillis());                  long percent = Math.round((100.0 * task.getTimeSeconds()) / getTotalTimeSeconds());                  sb.append(" = ").append(percent).append("%");              }          } else {              sb.append("; no task info kept");          }          return sb.toString();      }          /**      * Inner class to hold data about one task executed within the stop watch.      */      public static final class TaskInfo {            private final String taskName;            private final long timeMillis;            TaskInfo(String taskName, long timeMillis) {              this.taskName = taskName;              this.timeMillis = timeMillis;          }            /**          * Return the name of this task.          */          public String getTaskName() {              return this.taskName;          }            /**          * Return the time in milliseconds this task took.          */          public long getTimeMillis() {              return this.timeMillis;          }            /**          * Return the time in seconds this task took.          */          public double getTimeSeconds() {              return this.timeMillis / 1000.0;          }      }            /**      * test      * @throws InterruptedException       */      public static void main(String[] args) throws InterruptedException{          StopWatch first = new StopWatch("First");          first.start("A");          Thread.sleep(200);          first.stop();          first.start("B");          Thread.sleep(200);          first.stop();          first.start("C");          Thread.sleep(120);          first.stop();          System.out.println(first.prettyPrint());                }  }  执行结果如下:

StopWatch 'First': running time (millis) = 516  -----------------------------------------  ms     %     Task name  -----------------------------------------  00203  039%  A  00203  039%  B  00110  021%  C 打印每个任务执行时间,以及占总时间百分比,个人开发测试时挺有用的,可以作为小工具收藏。


发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表