/*++ Copyright (c) 2008 Microsoft Corporation Module Name: stopwatch.h Abstract: High resolution time keeping Author: Christoph Wintersteiger (t-cwinte) 2008-12-24 Revision History: --*/ #pragma once #include "util/debug.h" #include #include #include class stopwatch { typedef decltype(std::chrono::steady_clock::now()) clock_t; typedef decltype(std::chrono::steady_clock::now() - std::chrono::steady_clock::now()) duration_t; clock_t m_start; duration_t m_elapsed; bool m_running = false; // FIXME: just use auto with VS 2015+ static clock_t get() { return std::chrono::steady_clock::now(); } public: stopwatch() { reset(); } void add(const stopwatch &s) { m_elapsed += s.m_elapsed; } void reset() { m_elapsed = duration_t::zero(); } void start() { if (!m_running) { m_start = get(); m_running = true; } } void stop() { if (m_running) { m_elapsed += get() - m_start; m_running = false; } } double get_seconds() const { if (m_running) { const_cast(this)->stop(); const_cast(this)->start(); } return std::chrono::duration_cast(m_elapsed).count() / 1000.0; } double get_current_seconds() const { return get_seconds(); } }; struct scoped_watch { stopwatch &m_sw; scoped_watch (stopwatch &sw, bool reset=false): m_sw(sw) { if (reset) m_sw.reset(); m_sw.start(); } ~scoped_watch() { m_sw.stop (); } }; inline std::ostream& operator<<(std::ostream& out, stopwatch const& sw) { return out << " :time " << std::fixed << std::setprecision(2) << sw.get_seconds(); }