libmoost
|
00001 /* vim:set ts=3 sw=3 sts=3 et: */ 00035 #ifndef MOOST_UTILS_STOPWATCH_HPP__ 00036 #define MOOST_UTILS_STOPWATCH_HPP__ 00037 00038 #include <boost/date_time/posix_time/posix_time.hpp> 00039 #include <boost/cstdint.hpp> 00040 #include <boost/noncopyable.hpp> 00041 00042 namespace moost { namespace utils { 00043 00048 class stopwatch : boost::noncopyable 00049 { 00050 public: 00051 00052 typedef boost::int64_t elapsed_t; 00053 00054 stopwatch() 00055 { 00056 restart(); 00057 } 00058 00059 void restart() 00060 { 00061 start_ = boost::posix_time::microsec_clock::universal_time(); 00062 } 00063 00064 elapsed_t elapsed_ns() const // nanosecs 00065 { 00066 boost::posix_time::ptime now = boost::posix_time::microsec_clock::universal_time(); 00067 return (now - start_).total_nanoseconds(); 00068 } 00069 00070 elapsed_t elapsed_us() const // microsecs (default) 00071 { 00072 boost::posix_time::ptime now = boost::posix_time::microsec_clock::universal_time(); 00073 return (now - start_).total_microseconds(); 00074 } 00075 00076 elapsed_t elapsed_ms() const // millisecs 00077 { 00078 boost::posix_time::ptime now = boost::posix_time::microsec_clock::universal_time(); 00079 return (now - start_).total_milliseconds(); 00080 } 00081 00082 elapsed_t elapsed_secs() const // secs 00083 { 00084 boost::posix_time::ptime now = boost::posix_time::microsec_clock::universal_time(); 00085 return (now - start_).total_seconds(); 00086 } 00087 00088 elapsed_t elapsed() const 00089 { 00090 return elapsed_us(); 00091 } 00092 00093 private: 00094 boost::posix_time::ptime start_; 00095 }; 00096 00101 class scoped_stopwatch : boost::noncopyable 00102 { 00103 public: 00104 enum granularity 00105 { 00106 nanosecs, microsecs, millisecs, secs 00107 }; 00108 00109 typedef stopwatch::elapsed_t elapsed_t; 00110 00111 scoped_stopwatch( 00112 elapsed_t & future, // This is a future, which will be assigned elapsed on destruction 00113 granularity const g = microsecs, // This is the granularity of elapsed (default is microsecs) 00114 bool const a = false // If true add elapsed to future else assign elapsed to future 00115 ) 00116 : future_(future), granularity_(g), accumulate_(a) 00117 { 00118 } 00119 00120 ~scoped_stopwatch() 00121 { 00122 elapsed_t e; 00123 00124 switch(granularity_) 00125 { 00126 case secs: 00127 e = sw_.elapsed_secs(); 00128 break; 00129 case millisecs: 00130 e = sw_.elapsed_ms(); 00131 break; 00132 case microsecs: 00133 e = sw_.elapsed_us(); 00134 break; 00135 case nanosecs: 00136 e = sw_.elapsed_ns(); 00137 break; 00138 default: 00139 e = sw_.elapsed(); 00140 break; 00141 } 00142 00143 future_ = e + (accumulate_ ? future_ : 0); 00144 } 00145 00146 private: 00147 stopwatch sw_; 00148 elapsed_t & future_; 00149 granularity const granularity_; 00150 bool const accumulate_; 00151 }; 00152 00153 }} 00154 00155 #endif // MOOST_UTILS_STOPWATCH_HPP__