More C++ Idioms/Nifty Counter

From Wikibooks, open books for an open world
Jump to: navigation, search

Contents

[edit]

Nifty Counter

[edit] Intent

Ensure a non-local static object is initialized before its first use and destroyed only after last use of the object.

[edit] Also Known As

Schwarz Counter

[edit] Motivation

When static objects use other static objects, the initialization problem becomes more complex. Static object must be initialized before its use if it has non-trivial initialization. Initialization order of static objects across compilation units is not well-defined. More than one static objects, spread across multiple compilation units, might be using a single static object. For example, std::cout. std::cout can be used in the number of other static objects. Therefore, it must be initialized before use.

[edit] Solution and Sample Code

Nifty counter idiom is an example of reference counting idiom applied to the initialization of static objects.

//Stream.hpp
class StreamInitializer;
 
class Stream {
   friend class StreamInitializer;
 public:
   Stream () {
   // Constructor must be called before use.
   }
};
static class StreamInitializer {
  public:
    StreamInitializer ();
    ~StreamInitializer ();
} initializer; //Note object here in the header.
//Stream.cpp
static int nifty_counter; 
// The counter is initialized at load-time i.e., before any of the static objects are initialized.
StreamInitializer::StreamInitializer ()
{
  if (0 == nifty_counter++)
  {
    // Initialize Stream object's static members.
  }
}
StreamInitializer::~StreamInitializer ()
{
  if (0 == --nifty_counter)
  {
    // Clean-up.
  }
}

The header file of Stream class has to be included before any member function can be called on the Stream object. An instance of class StreamInitializer (called initializer) is included in each compilation unit. Any use of the Stream object follows after the inclusion of header, which ensures that the constructor of the initializer object is called before the Stream object is used.

[edit] Known Uses

Standard C++ iostream library std::cout, std::cin, std::cerr, std::clog.

[edit] Related Idioms

[edit] References

Personal tools
Namespaces
Variants
Actions
Navigation
Community
Toolbox
In other languages
Sister projects
Print/export