Teuchos Package Browser (Single Doxygen Collection) Version of the Day
Teuchos_PerformanceMonitorBase.hpp
Go to the documentation of this file.
00001 // @HEADER
00002 // ***********************************************************************
00003 //
00004 //                    Teuchos: Common Tools Package
00005 //                 Copyright (2004) Sandia Corporation
00006 //
00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
00008 // license for use of this work by or on behalf of the U.S. Government.
00009 //
00010 // Redistribution and use in source and binary forms, with or without
00011 // modification, are permitted provided that the following conditions are
00012 // met:
00013 //
00014 // 1. Redistributions of source code must retain the above copyright
00015 // notice, this list of conditions and the following disclaimer.
00016 //
00017 // 2. Redistributions in binary form must reproduce the above copyright
00018 // notice, this list of conditions and the following disclaimer in the
00019 // documentation and/or other materials provided with the distribution.
00020 //
00021 // 3. Neither the name of the Corporation nor the names of the
00022 // contributors may be used to endorse or promote products derived from
00023 // this software without specific prior written permission.
00024 //
00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00036 //
00037 // Questions? Contact Michael A. Heroux (maherou@sandia.gov)
00038 //
00039 // ***********************************************************************
00040 // @HEADER
00041 
00042 #ifndef TEUCHOS_PERFORMANCEMONITORBASE_H
00043 #define TEUCHOS_PERFORMANCEMONITORBASE_H
00044 
00050 #include "Teuchos_ConfigDefs.hpp"
00051 #include "Teuchos_Comm.hpp"
00052 #include "Teuchos_RCP.hpp"
00053 #include "Teuchos_Array.hpp"
00054 #include "Teuchos_TableFormat.hpp"
00055 
00056 namespace Teuchos
00057 {
00065   enum ECounterSetOp { Intersection, Union };
00066 
00091   void
00092   mergeCounterNames (const Comm<int>& comm, 
00093          const Array<std::string>& localNames,
00094          Array<std::string>& globalNames,
00095          const ECounterSetOp setOp);
00096 
00140   template <class T> 
00141   class PerformanceMonitorBase
00142   {
00143   public:
00145     PerformanceMonitorBase(T& counter_in, bool reset=false)
00146       : counter_(counter_in), isRecursiveCall_(counter_.isRunning())
00147     {
00148       (void)reset;  // get rid of "unused parameter" warning
00149       counter_.incrementNumCalls();
00150     }
00151 
00156     virtual ~PerformanceMonitorBase() {}
00157     
00168     static RCP<T> getNewCounter(const std::string& name)
00169     {
00170       RCP<T> rtn = rcp(new T(name), true);
00171       counters().append(rtn);
00172       return rtn;
00173     }
00174 
00176     static TableFormat& format()
00177     {
00178       // WARNING This is not thread safe!  In particular, if multiple
00179       // threads call this method for the "first time" at the same
00180       // time, the RCP may be initialized incorrectly.
00181       static RCP<TableFormat> rtn=rcp(new TableFormat()); 
00182       return *rtn; 
00183     }
00184 
00205     static RCP<T> 
00206     lookupCounter (const std::string& name);
00207 
00212     static void clearCounters ();
00213 
00223     static TEUCHOS_DEPRECATED void clearTimers ();
00224 
00230     static void clearCounter (const std::string& name);
00231 
00242     static TEUCHOS_DEPRECATED void clearTimer (const std::string& name);
00243 
00244   protected:
00245     
00247     const T& counter() const { return counter_; }
00248     
00250     T& counter() { return counter_; }
00251 
00258     bool isRecursiveCall() const { return isRecursiveCall_; }
00259       
00261     static Array<RCP<T> >& counters() 
00262     {
00263       // Use the "Meyers Trick" to create static data safely.
00264       //
00265       // WARNING This is not thread safe!  In particular, if multiple
00266       // threads call counters() for the "first time" at the same
00267       // time, the array may be initialized incorrectly.
00268       static Array<RCP<T> > rtn;
00269       return rtn;
00270     }
00271 
00272   private:
00273 
00275     T& counter_;
00276     
00278     bool isRecursiveCall_;
00279   };
00280 
00281 
00282   template<class T>
00283   RCP<T> 
00284   PerformanceMonitorBase<T>::lookupCounter (const std::string& name)
00285   {
00286     Array<RCP<T> >& ctrs = counters();
00287 
00288     // This will have to change if we change how we store the
00289     // counters.
00290     for (typename Array<RCP<T> >::const_iterator it = ctrs.begin(); 
00291    it != ctrs.end(); ++it)
00292       if ((*it)->name() == name)
00293   return *it;
00294       
00295     return null;
00296   }
00297 
00298   template<class T>
00299   void
00300   PerformanceMonitorBase<T>::clearCounter (const std::string& name)
00301   {
00302     Array<RCP<T> > newCounters;
00303     // Only fill newCounters with counters whose name is not the given
00304     // name to clear.  Then, swap newCounters with the old list of
00305     // counters.
00306     typedef typename Array<RCP<T> >::const_iterator iter_t;
00307     for (iter_t it = counters().begin(); it != counters().end(); ++it)
00308       {
00309   // The variable 'it' is an Array iterator; '*it' is a 'const
00310   // RCP<T>&'.  We want the latter.
00311   if ((*it)->name() != name)
00312     newCounters.push_back (*it);
00313       }
00314     counters().swap (newCounters);
00315   }
00316 
00317   template<class T>
00318   void
00319   PerformanceMonitorBase<T>::clearTimer (const std::string& name)
00320   {
00321     clearCounter (name);
00322   }
00323 
00324   template<class T>
00325   void
00326   PerformanceMonitorBase<T>::clearTimers ()
00327   {
00328     clearCounters ();
00329   }
00330 
00331   template<class T>
00332   void
00333   PerformanceMonitorBase<T>::clearCounters ()
00334   {
00335     // Just resizing an Array to have length zero may not necessarily
00336     // free its storage.  The standard idiom is to swap with an empty
00337     // array.
00338     Array<RCP<T> > newCounters;
00339     counters().swap (newCounters);
00340   }
00341   
00342 } // namespace Teuchos
00343 
00344 #endif // TEUCHOS_PERFORMANCEMONITORBASE_H
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines