Boost logo

Boost :

Subject: Re: [boost] [system] Boost.Timer replacement
From: Beman Dawes (bdawes_at_[hidden])
Date: 2011-09-25 08:29:09


On Tue, Sep 20, 2011 at 10:56 AM, Vicente Botet
<vicente.botet_at_[hidden]> wrote:
>
> Stewart, Robert wrote:
>>
>>
>> I dislike the idea of relying on a destructor to report timing information
>> as you've done in run_timer.  The no-throw demands of a destructor make
>> I/O questionable since there is no means to report failure.  I realize
>> that there is a report() member function that can be called separately,
>> but using the destructor just seems too odd.
>>
>
> Yes, reporting on the destructor would imply to catch any exception.
>
> I have used the word stopwatch instead. From wikipedia:
> "A timer can be used to control the sequence of an event or process. Whereas
> a stopwatch counts upwards from zero for measuring elapsed time, a timer
> counts down from a specified time interval, like an hourglass."

I've decided that the best place for the functionality is the current
timer library, so will stick with the "timer" terminology.

Also, real stopwatches (I own one!) often have "lap" functionality,
too, and that isn't supplied by these classes.

But "stopwatch" might be a great name for Boost.Chrono use.

>> "run_timer" doesn't indicating the principle feature: reporting.  You
>> might call it "reporting_timer" or "reportable_timer"?
>>
>
> I have used stopwatch_reporter.

I ended up folding that functionality into the base class.

>> "report" does not imply a call to stop().

Agreed. But leaving the timer running while doing I/O seems likely to
produce misleading results. I've added a note to the docs.

>>
>> Because of all of those strikes against run_timer, I'd prefer something
>> like this:
>>
>> class timer
>> {
>> public:
>>    // as before
>>
>>    void
>>    report(int _places = 2); // writes to std::cout
>>
>>    void
>>    report(int _places, std::ostream & _stream);
>>
>>    void
>>    report(std::string const & _format, int _places = 2);
>>
>>    void
>>    report(std::string const & _format, int _places,
>>       std::ostream & _stream);
>> };
>>
>
> I guess that we need reporters that are independent of the timer/stopwatch.

I've added independent format() functions to deal with that need.

>> Those member functions would capture a snapshot of the elapsed time and
>> report it.  (That means the I/O would affect further timing values; an
>> accumulated elapsed time and a current start time could be used to ignore
>> the time required for I/O.)  A call to stop() followed by a call to
>> report() would be needed to report the elapsed time.
>>
>> It still might be useful to provide an RAII class to ensure a timer stops
>> at the end of a scope:
>>
>> timer t;
>> {
>>    stopper _(t);
>>    // do stuff
>> }
>>
>>
>
> Yes, this will be safer. I had some scoped runner, stopper, suspender,
> resumer that could be used for these purpose
>
> stopwatch<> sw(dont_start);
> {
>   scoped_runner<> _(sw); //starts on construction + stop on destruction
>   // do stuff
>  {
>     scoped_suspender<> _(sw); // suspend on construction + resume on
> destruction
>     // do some stuff we don't want to measure, as e.g. i/o.
>  }
> }
>
> We could provide some specific stopwatch formatters that could make easier
> the reporting as for example
>
> cout << times_stopwatch_fmt("xxxx real=%1% user=%2% system=%3") % sw;
>
> The single line run_timer from Beman is yet quite attractive and the library
> could warn to the user of its limitations. I have tried to make a kind of
> 'generic' stopwatch reporter but at the end it relies always on a Formatter
> class which of course can have a valid default.

Yes. Boost.Chrono is the right place for stopwatches, reporters, and
formatters with a wide selection of features. I want to keep timer use
simple.

--Beman


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk