1 /*! \file
2 \verbatim
3
4 Copyright (c) 2006, Sylvain Paris and Fr�do Durand
5
6 Permission is hereby granted, free of charge, to any person
7 obtaining a copy of this software and associated documentation
8 files (the "Software"), to deal in the Software without
9 restriction, including without limitation the rights to use, copy,
10 modify, merge, publish, distribute, sublicense, and/or sell copies
11 of the Software, and to permit persons to whom the Software is
12 furnished to do so, subject to the following conditions:
13
14 The above copyright notice and this permission notice shall be
15 included in all copies or substantial portions of the Software.
16
17 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20 NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
21 HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
22 WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
24 DEALINGS IN THE SOFTWARE.
25
26 \endverbatim
27 */
28
29
30
31 #ifndef __CHRONO__
32 #define __CHRONO__
33
34 #include <ctime>
35
36 #include <iostream>
37 #include <sstream>
38 #include <string>
39
40 #include "msg_stream.h"
41
42 class Chrono{
43
44 public:
45 inline Chrono(const std::string t=std::string());
46
47 inline void start();
48 inline void stop();
49 inline void reset();
50
51 inline std::string report();
52 inline std::string time_report();
53
54 inline float time_in_seconds();
55
56 inline ~Chrono();
57
58 private:
59 const std::string title;
60
61 bool is_started;
62 bool reported;
63 std::clock_t start_clock;
64 std::clock_t cumulative_clock;
65 unsigned int n_starts;
66 };
67
68
69
70 /*
71
72 #############################################
73 #############################################
74 #############################################
75 ###### ######
76 ###### I M P L E M E N T A T I O N ######
77 ###### ######
78 #############################################
79 #############################################
80 #############################################
81
82 */
83
84
Chrono(const std::string t)85 Chrono::Chrono(const std::string t):
86 title(t),
87 is_started(false),
88 reported(false),
89 start_clock(0),
90 cumulative_clock(0),
91 n_starts(0){
92
93 }
94
95
start()96 void Chrono::start(){
97
98 if (is_started){
99 Message::warning<<"Chrono '"<<title<<"' is already started. Nothing done."<<Message::done;
100 return;
101 }
102
103 is_started = true;
104 n_starts++;
105 start_clock = std::clock();
106 }
107
108
stop()109 void Chrono::stop(){
110 if (!is_started){
111 Message::warning<<"Chrono '"<<title<<"' is not started. Nothing done."<<Message::done;
112 return;
113 }
114
115 cumulative_clock += std::clock() - start_clock;
116 is_started = false;
117 }
118
119
reset()120 void Chrono::reset(){
121 if (is_started){
122 Message::warning<<"Chrono '"<<title<<"' is started during reset request.\n Only reset cumulative time."<<Message::done;
123 return;
124 }
125
126 cumulative_clock = 0;
127 }
128
129
report()130 std::string Chrono::report(){
131 if (is_started){
132 Message::warning<<"Chrono '"<<title<<"' is started.\n Cannot provide a report."<<Message::done;
133 return std::string();
134 }
135
136 std::ostringstream msg;
137 msg<<"["<<title<<"] cumulative time: "<<(static_cast<float>(cumulative_clock)/CLOCKS_PER_SEC)
138 <<"s\t#run: "<<n_starts<<"\taverage time: "
139 <<(static_cast<float>(cumulative_clock)/CLOCKS_PER_SEC/n_starts)<<"s";
140 reported = true;
141 return msg.str();
142 }
143
144
time_report()145 std::string Chrono::time_report(){
146 if (is_started){
147 Message::warning<<"Chrono '"<<title<<"' is started.\n Cannot provide a time report."<<Message::done;
148 return std::string();
149 }
150
151 std::ostringstream msg;
152 msg<<(static_cast<float>(cumulative_clock)/CLOCKS_PER_SEC);
153 reported = true;
154 return msg.str();
155 }
156
157
time_in_seconds()158 float Chrono::time_in_seconds(){
159
160 if (is_started){
161 Message::warning<<"Chrono '"<<title<<"' is started.\n Cannot provide a time measure."<<Message::done;
162 }
163
164 reported = true;
165
166 return static_cast<float>(cumulative_clock) / CLOCKS_PER_SEC;
167 }
168
169
~Chrono()170 Chrono::~Chrono(){
171 if (is_started){
172 Message::warning<<"Chrono '"<<title<<"' is started and is being destroyed."<<Message::done;
173 stop();
174 }
175
176 if (!reported){
177 Message::warning<<"Chrono '"<<title<<"' is destroyed without having given its result.\n"
178 <<report()<<Message::done;
179
180 }
181 }
182
183
184
185 #endif
186