1 /* "CodeWorker":	a scripting language for parsing and generating text.
2 
3 Copyright (C) 1996-1997, 1999-2002 C�dric Lemaire
4 
5 This library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
9 
10 This library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13 Lesser General Public License for more details.
14 
15 You should have received a copy of the GNU Lesser General Public
16 License along with this library; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18 
19 To contact the author: codeworker@free.fr
20 
21 This implementation is strongly inspired of 'SWORD::Chronograph', written by
22 Eric NICOLAS.
23 */
24 
25 #ifndef _UtlTimer_h_
26 #define _UtlTimer_h_
27 
28 namespace CodeWorker {
29 	/*! A Chronograph for measuring time spent in code. Each
30 	 *  instance of this class accumulates time spent by your
31 	 *  program between calls to start() and stop(). The time
32 	 *  can then be retrieved by getTimeInMillis() and
33 	 *  getTimeInSec().
34 	 *
35 	 *  Example:
36 	 *  \code
37 	 *    Chronograph c;
38 	 *    c.start();
39 	 *    for(int i=0; i<10000; ++i) { / * do stuff * / }
40 	 *    c.stop();
41 	 *    cout << "Spent = " << c.getTimeInSec() << " seconds" << endl;
42 	 *  \endcode
43 	 */
44 
45 #ifdef WIN32
46 	typedef signed   __int64       int64;
47 	typedef unsigned __int64       word64;
48 #else
49 	typedef signed   long long int int64;
50 	typedef unsigned long long int word64;
51 #endif
52 
53 	class UtlTimer {
54 		int64  start_;
55 		int64  elapsed_;
56 		int64  freqInMillis_;
57 		double freqInSec_;
58 		bool   active_;
59 
60 	public:
61 		/*! Creates a Chronograph. The time measurement is not
62 		 *  started yet. You must call start() once to start
63 		 *  the chronograph.
64 		 */
UtlTimer()65 		inline UtlTimer() {
66 			clear();
67 			freqInMillis_ = freq() / 1000;
68 			freqInSec_    = (double)freq();
69 		}
70 
~UtlTimer()71 		inline ~UtlTimer() {}
72 
73 		/*! Clear (reset) the Chronograph. The accumulated elapsed
74 		 *  time is lost, and you have to call start() again to
75 		 *  start measuring again
76 		 */
clear()77 		inline void clear() {
78 			start_ = elapsed_ = 0;
79 			active_ = false;
80 		}
81 
82 		/*! Start measuring time.
83 		 *  \see start, getTimeInMillis, getTimeInSec
84 		 */
start()85 		inline void start() {
86 			start_ = now();
87 			active_ = true;
88 		}
89 
90 		/*! Stops measuring time. The time elapsed between the
91 		 *  last call to start() and this call is accumulated in
92 		 *  the chronograph
93 		 *  \see start, getTimeInMillis, getTimeInSec
94 		 */
stop()95 		inline void stop() {
96 			elapsed_ += (now() - start_);
97 			active_ = false;
98 		}
99 
100 		/*! Get the accumulated time in milliseconds. This method can
101 		 *  be called either 'during measurement' (between a start()
102 		 *  and a stop() ), or 'post morten' (after a stop() ).
103 		 *  \see getTimeInSec, start, stop
104 		 */
105 		unsigned long getTimeInMillis();
106 
107 		/*! Get the accumulated time in seconds, with more precision
108 		 *  in the decimal part of the returned value. This method can
109 		 *  be called either 'during measurement' (between a start()
110 		 *  and a stop() ), or 'post morten' (after a stop() ).
111 		 *  \see getTimeInMillis, start, stop
112 		 */
getTimeInSec()113 		inline double getTimeInSec() {
114 			if (active_) {
115 				stop();
116 				start();
117 			}
118 			return (double) elapsed_ / freqInSec_;
119 		}
120 
121 	private:
122 		// The two platform-dependant methods
123 		static int64 now();   // gets the current timestamp
124 		static int64 freq();  // gets the resolution of now()
125 	};
126 }
127 
128 #endif
129