StateFull vs Stateless Singleton

Discussion in 'C++' started by Pallav singh, Jul 4, 2010.

  1. Pallav singh

    Pallav singh Guest

    Hi

    what the consideration parameter to choose stateless and statefull
    Singleton ?

    Thanks
    Pallav Singh
     
    Pallav singh, Jul 4, 2010
    #1
    1. Advertising

  2. Pallav singh <>, on 04/07/2010 07:02:05, wrote:

    > Hi
    >
    > what the consideration parameter to choose stateless and statefull
    > Singleton ?


    The mere need of a "stateless singleton" seems to be debatable - since
    the things it can achieve can equally be achieved via regular functions
    and static member functions - assuming I haven't completely
    misunderstood them, any correction from better knowing will be welcome.

    In any case, the considerations to make (in general) lie upon the
    requirements of the single cases. Have you got any practical example to
    consider?

    --
    FSC - http://userscripts.org/scripts/show/59948
    http://fscode.altervista.org - http://sardinias.com
     
    Francesco S. Carta, Jul 4, 2010
    #2
    1. Advertising

  3. Pallav singh

    Öö Tiib Guest

    On 4 juuli, 17:02, Pallav singh <> wrote:
    > Hi
    >
    > what the consideration parameter to choose stateless and statefull
    > Singleton ?


    Both are sort of java nonsense to achieve non-copyable global state or
    global functions that java does not let you have otherwise. Global
    state is bad design in all languages. Global functions are fine, but
    you do not need singeltons for them in C++.
     
    Öö Tiib, Jul 4, 2010
    #3
  4. Pallav singh

    Trifle Menot Guest

    On Sun, 4 Jul 2010 08:42:25 -0700 (PDT), Öö Tiib <> wrote:

    >Global state is bad design in all languages.


    Not for small programs where you're the sole author. Things should be
    as simple as possible.



    --
    Web mail, POP3, and SMTP
    http://www.beewyz.com/freeaccounts.php
     
    Trifle Menot, Jul 4, 2010
    #4
  5. Pallav singh

    sebastian Guest

    On Jul 4, 9:02 am, Pallav singh <> wrote:
    > Hi
    >
    > what the consideration parameter to choose stateless and statefull
    > Singleton ?
    >
    > Thanks
    > Pallav Singh


    Neither - a simple template class eliminates the issue altogether:

    <code>

    #include <stdexcept>

    template < typename Type >
    class singleton
    {
    public:

    singleton( void )
    {
    Type* ptr = static_cast< Type* >( this );
    if( self )
    {
    /*
    Or what have you...
    */
    throw std::runtime_error
    (
    "Error: attempt to instantiate multiple instances of a singleton"
    );
    }
    self = ptr;
    }

    static inline Type& instance( void )
    {
    return *self;
    }

    static inline bool exists( void )
    {
    return self != 0;
    }

    virtual ~singleton( void )
    {
    self = 0;
    }

    private:

    singleton( singleton const& );

    singleton& operator = ( singleton const& );

    static Type* self;
    };

    template < typename Type >
    Type* singleton< Type >::self = 0;

    // Example:

    #include <iostream>

    class foo : public singleton< foo >
    {
    public:

    void bar( void ) const
    {
    std::cout << "foo::bar( )" << std::endl;
    }
    };

    int main( void )
    {
    try
    {
    foo a;
    foo::instance( ).bar( );
    foo c; // Whoops!
    foo::instance( ).bar( );
    }
    catch( std::exception const& error )
    {
    std::cerr << error.what( ) << std::endl;
    }
    }

    </code>

    The beauty of the design is that it allows the user to decide how to
    allocate and initialize the derived class; it's sole purpose is to
    make sure that multiple instances aren't created. Best of all, it's
    completely generic!

    Cheers.
     
    sebastian, Jul 4, 2010
    #5
  6. Pallav singh

    Öö Tiib Guest

    On 4 juuli, 23:58, sebastian <> wrote:
    > On Jul 4, 9:02 am, Pallav singh <> wrote:
    >
    > > Hi

    >
    > > what the consideration parameter to choose stateless and statefull
    > > Singleton ?

    >
    > > Thanks
    > > Pallav Singh

    >
    > Neither - a simple template class eliminates the issue altogether:
    >
    > <code>
    >
    > #include <stdexcept>
    >
    > template < typename Type >
    > class singleton
    > {
    >         public:
    >
    >         singleton( void )
    >         {
    >                 Type* ptr = static_cast< Type* >( this );
    >                 if( self )
    >                 {
    >                 /*
    >                         Or what have you...
    >                 */
    >                         throw std::runtime_error
    >                         (
    >                                 "Error: attempt to instantiate multiple instances of a singleton"
    >                         );
    >                 }
    >                 self = ptr;
    >         }
    >
    >         static inline Type& instance( void )
    >         {
    >                 return *self;
    >         }
    >
    >         static inline bool exists( void )
    >         {
    >                 return self != 0;
    >         }
    >
    >         virtual ~singleton( void )
    >         {
    >                 self = 0;
    >         }
    >
    >         private:
    >
    >         singleton( singleton const& );
    >
    >         singleton& operator = ( singleton const& );
    >
    >         static Type* self;
    >
    > };
    >
    > template < typename Type >
    > Type* singleton< Type >::self = 0;
    >
    > // Example:
    >
    > #include <iostream>
    >
    > class foo : public singleton< foo >
    > {
    >         public:
    >
    >         void bar( void ) const
    >         {
    >                 std::cout << "foo::bar( )" << std::endl;
    >         }
    >
    > };
    >
    > int main( void )
    > {
    >         try
    >         {
    >                 foo a;
    >                 foo::instance( ).bar( );
    >                 foo c; // Whoops!
    >                 foo::instance( ).bar( );
    >         }
    >         catch( std::exception const& error )
    >         {
    >                 std::cerr << error.what( ) << std::endl;
    >         }
    >
    > }
    >
    > </code>
    >
    > The beauty of the design is that it allows the user to decide how to
    > allocate and initialize the derived class; it's sole purpose is to
    > make sure that multiple instances aren't created. Best of all, it's
    > completely generic!
    >
    > Cheers.


    Looks as beautiful like any other reinvented square wheel. The
    requirements seem to be that such code must work:

    int main( void )
    {
    {
    foo a;
    foo::instance( ).bar( );
    }
    foo c; // Second singleton and *NO* Whoops
    foo::instance( ).bar( );
    }

    Not sure why someone needs to have global state? Typical example of
    singletons is a logger. Huh? So ... OK. What if i need to have
    separate logs from different modules? I will then need new class for
    each log to have separate singleton logger for each module? Nonsense.

    What if i need to have separate logs from different threads? Then that
    Logger::instance() should give me "different" singletons based on
    thread ID? Huh? Why it can't just be debugging::log() and where it
    logs is its internal business, no global state no nothing?

    As for your code ... same thing with 10-12 lines instead of 70-80:

    #include <iostream>
    namespace foo
    {
    void bar()
    {
    std::cout << "foo::bar()" << std::endl;
    }
    }

    int main()
    {
    foo::bar();
    }

    Things that contain nothing are not worth allocating or initializing.
     
    Öö Tiib, Jul 5, 2010
    #6
  7. On Jul 4, 7:31 pm, Öö Tiib <> wrote:
    > On 4 juuli, 23:58, sebastian <> wrote:
    > > On Jul 4, 9:02 am, Pallav singh <> wrote:

    >
    > > > Hi

    >
    > > > what the consideration parameter to choose stateless and statefull
    > > > Singleton ?

    >
    > > Neither - a simple template class eliminates the issue altogether:
    > >
    > > ...
    > >
    > > The beauty of the design is that it allows the user to decide how to
    > > allocate and initialize the derived class; it's sole purpose is to
    > > make sure that multiple instances aren't created. Best of all, it's
    > > completely generic!

    >
    > Looks as beautiful like any other reinvented square wheel. The
    > requirements seem to be that such code must work:
    >
    > ...
    >
    > Not sure why someone needs to have global state? Typical example of
    > singletons is a logger. Huh? So ... OK. What if i need to have
    > separate logs from different modules? I will then need new class for
    > each log to have separate singleton logger for each module? Nonsense.


    Yeah, it seems to me that singleton is the single most heavily
    abused design pattern. Maybe because its name is "cool sounding"
    and because it is easy to implement and because it allows one to
    remain lazy maybe those are a trifecta of abuse temptations.

    I think the only pattern I've seen nearly as heavily abused (but
    at least not reimplemented as often) is shared_ptr where some crap
    coder(s) spams every pointer as a shared_ptr because of irrational
    fear and/or unwillingness (or inability) to design proper lifetime
    management or to eliminate the need for such management entirely.

    KHD
     
    Keith H Duggar, Jul 5, 2010
    #7
  8. Pallav singh

    sebastian Guest

    On Jul 4, 6:31 pm, Öö Tiib <> wrote:
    > On 4 juuli, 23:58, sebastian <> wrote:
    >
    >
    >
    > > On Jul 4, 9:02 am, Pallav singh <> wrote:

    >
    > > > Hi

    >
    > > > what the consideration parameter to choose stateless and statefull
    > > > Singleton ?

    >
    > > > Thanks
    > > > Pallav Singh

    >
    > > Neither - a simple template class eliminates the issue altogether:

    >
    > > <code>

    >
    > > #include <stdexcept>

    >
    > > template < typename Type >
    > > class singleton
    > > {
    > >         public:

    >
    > >         singleton( void )
    > >         {
    > >                 Type* ptr = static_cast< Type* >( this );
    > >                 if( self )
    > >                 {
    > >                 /*
    > >                         Or what have you...
    > >                 */
    > >                         throw std::runtime_error
    > >                         (
    > >                                 "Error: attempt to instantiate multiple instances of a singleton"
    > >                         );
    > >                 }
    > >                 self = ptr;
    > >         }

    >
    > >         static inline Type& instance( void )
    > >         {
    > >                 return *self;
    > >         }

    >
    > >         static inline bool exists( void )
    > >         {
    > >                 return self != 0;
    > >         }

    >
    > >         virtual ~singleton( void )
    > >         {
    > >                 self = 0;
    > >         }

    >
    > >         private:

    >
    > >         singleton( singleton const& );

    >
    > >         singleton& operator = ( singleton const& );

    >
    > >         static Type* self;

    >
    > > };

    >
    > > template < typename Type >
    > > Type* singleton< Type >::self = 0;

    >
    > > // Example:

    >
    > > #include <iostream>

    >
    > > class foo : public singleton< foo >
    > > {
    > >         public:

    >
    > >         void bar( void ) const
    > >         {
    > >                 std::cout << "foo::bar( )" << std::endl;
    > >         }

    >
    > > };

    >
    > > int main( void )
    > > {
    > >         try
    > >         {
    > >                 foo a;
    > >                 foo::instance( ).bar( );
    > >                 foo c; // Whoops!
    > >                 foo::instance( ).bar( );
    > >         }
    > >         catch( std::exception const& error )
    > >         {
    > >                 std::cerr << error.what( ) << std::endl;
    > >         }

    >
    > > }

    >
    > > </code>

    >
    > > The beauty of the design is that it allows the user to decide how to
    > > allocate and initialize the derived class; it's sole purpose is to
    > > make sure that multiple instances aren't created. Best of all, it's
    > > completely generic!

    >
    > > Cheers.

    >
    > Looks as beautiful like any other reinvented square wheel. The
    > requirements seem to be that such code must work:
    >
    >  int main( void )
    >  {
    >      {
    >          foo a;
    >          foo::instance( ).bar( );
    >      }
    >      foo c; // Second singleton and *NO* Whoops
    >      foo::instance( ).bar( );
    >  }
    >
    > Not sure why someone needs to have global state? Typical example of
    > singletons is a logger. Huh? So ... OK. What if i need to have
    > separate logs from different modules? I will then need new class for
    > each log to have separate singleton logger for each module? Nonsense.
    >
    > What if i need to have separate logs from different threads? Then that
    > Logger::instance() should give me "different" singletons based on
    > thread ID? Huh? Why it can't just be debugging::log() and where it
    > logs is its internal business, no global state no nothing?
    >
    > As for your code ... same thing with 10-12 lines instead of 70-80:
    >
    >  #include <iostream>
    >  namespace foo
    >  {
    >      void bar()
    >      {
    >          std::cout << "foo::bar()" << std::endl;
    >      }
    >  }
    >
    >  int main()
    >  {
    >      foo::bar();
    >  }
    >
    > Things that contain nothing are not worth allocating or initializing.


    So...your point is that you hate the singleton pattern? Got it. I hate
    it when people post snarky comments for no apparent reason,
    personally. To each his (and her) own, I guess.

    Cheers.
     
    sebastian, Jul 5, 2010
    #8
  9. Pallav singh

    Pallav singh Guest

    On Jul 5, 7:48 am, sebastian <> wrote:
    > On Jul 4, 6:31 pm, Öö Tiib <> wrote:
    >
    >
    >
    > > On 4 juuli, 23:58, sebastian <> wrote:

    >
    > > > On Jul 4, 9:02 am, Pallav singh <> wrote:

    >
    > > > > Hi

    >
    > > > > what the consideration parameter to choose stateless and statefull
    > > > > Singleton ?

    >
    > > > > Thanks
    > > > > Pallav Singh

    >
    > > > Neither - a simple template class eliminates the issue altogether:

    >
    > > > <code>

    >
    > > > #include <stdexcept>

    >
    > > > template < typename Type >
    > > > class singleton
    > > > {
    > > >         public:

    >
    > > >         singleton( void )
    > > >         {
    > > >                 Type* ptr = static_cast< Type* >( this );
    > > >                 if( self )
    > > >                 {
    > > >                 /*
    > > >                         Or what have you...
    > > >                 */
    > > >                         throw std::runtime_error
    > > >                         (
    > > >                                 "Error: attempt to instantiate multiple instances of a singleton"
    > > >                         );
    > > >                 }
    > > >                 self = ptr;
    > > >         }

    >
    > > >         static inline Type& instance( void )
    > > >         {
    > > >                 return *self;
    > > >         }

    >
    > > >         static inline bool exists( void )
    > > >         {
    > > >                 return self != 0;
    > > >         }

    >
    > > >         virtual ~singleton( void )
    > > >         {
    > > >                 self = 0;
    > > >         }

    >
    > > >         private:

    >
    > > >         singleton( singleton const& );

    >
    > > >         singleton& operator = ( singleton const& );

    >
    > > >         static Type* self;

    >
    > > > };

    >
    > > > template < typename Type >
    > > > Type* singleton< Type >::self = 0;

    >
    > > > // Example:

    >
    > > > #include <iostream>

    >
    > > > class foo : public singleton< foo >
    > > > {
    > > >         public:

    >
    > > >         void bar( void ) const
    > > >         {
    > > >                 std::cout << "foo::bar( )" << std::endl;
    > > >         }

    >
    > > > };

    >
    > > > int main( void )
    > > > {
    > > >         try
    > > >         {
    > > >                 foo a;
    > > >                 foo::instance( ).bar( );
    > > >                 foo c; // Whoops!
    > > >                 foo::instance( ).bar( );
    > > >         }
    > > >         catch( std::exception const& error )
    > > >         {
    > > >                 std::cerr << error.what( ) << std::endl;
    > > >         }

    >
    > > > }

    >
    > > > </code>

    >
    > > > The beauty of the design is that it allows the user to decide how to
    > > > allocate and initialize the derived class; it's sole purpose is to
    > > > make sure that multiple instances aren't created. Best of all, it's
    > > > completely generic!

    >
    > > > Cheers.

    >
    > > Looks as beautiful like any other reinvented square wheel. The
    > > requirements seem to be that such code must work:

    >
    > >  int main( void )
    > >  {
    > >      {
    > >          foo a;
    > >          foo::instance( ).bar( );
    > >      }
    > >      foo c; // Second singleton and *NO* Whoops
    > >      foo::instance( ).bar( );
    > >  }

    >
    > > Not sure why someone needs to have global state? Typical example of
    > > singletons is a logger. Huh? So ... OK. What if i need to have
    > > separate logs from different modules? I will then need new class for
    > > each log to have separate singleton logger for each module? Nonsense.

    >
    > > What if i need to have separate logs from different threads? Then that
    > > Logger::instance() should give me "different" singletons based on
    > > thread ID? Huh? Why it can't just be debugging::log() and where it
    > > logs is its internal business, no global state no nothing?

    >
    > > As for your code ... same thing with 10-12 lines instead of 70-80:

    >
    > >  #include <iostream>
    > >  namespace foo
    > >  {
    > >      void bar()
    > >      {
    > >          std::cout << "foo::bar()" << std::endl;
    > >      }
    > >  }

    >
    > >  int main()
    > >  {
    > >      foo::bar();
    > >  }

    >
    > > Things that contain nothing are not worth allocating or initializing.

    >
    > So...your point is that you hate the singleton pattern? Got it. I hate
    > it when people post snarky comments for no apparent reason,
    > personally. To each his (and her) own, I guess.
    >
    > Cheers.


    +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
    +++++++++
    +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
    +++++++++

    Hi

    Q How does Polymorphism get implemented in Singleton ?
    Q can we modify basic Singleton in such a way that all the class that
    Inherit it become Singleton ?

    Thanks
    Pallav
     
    Pallav singh, Jul 5, 2010
    #9
  10. Pallav singh

    Öö Tiib Guest

    On 5 juuli, 05:48, sebastian <> wrote:
    > On Jul 4, 6:31 pm, Öö Tiib <> wrote:
    >
    >
    >
    > > On 4 juuli, 23:58, sebastian <> wrote:

    >
    > > > On Jul 4, 9:02 am, Pallav singh <> wrote:

    >
    > > > > Hi

    >
    > > > > what the consideration parameter to choose stateless and statefull
    > > > > Singleton ?

    >
    > > > > Thanks
    > > > > Pallav Singh

    >
    > > > Neither - a simple template class eliminates the issue altogether:

    >
    > > > <code>

    >
    > > > #include <stdexcept>

    >
    > > > template < typename Type >
    > > > class singleton
    > > > {
    > > >         public:

    >
    > > >         singleton( void )
    > > >         {
    > > >                 Type* ptr = static_cast< Type* >( this );
    > > >                 if( self )
    > > >                 {
    > > >                 /*
    > > >                         Or what have you...
    > > >                 */
    > > >                         throw std::runtime_error
    > > >                         (
    > > >                                 "Error: attempt to instantiate multiple instances of a singleton"
    > > >                         );
    > > >                 }
    > > >                 self = ptr;
    > > >         }

    >
    > > >         static inline Type& instance( void )
    > > >         {
    > > >                 return *self;
    > > >         }

    >
    > > >         static inline bool exists( void )
    > > >         {
    > > >                 return self != 0;
    > > >         }

    >
    > > >         virtual ~singleton( void )
    > > >         {
    > > >                 self = 0;
    > > >         }

    >
    > > >         private:

    >
    > > >         singleton( singleton const& );

    >
    > > >         singleton& operator = ( singleton const& );

    >
    > > >         static Type* self;

    >
    > > > };

    >
    > > > template < typename Type >
    > > > Type* singleton< Type >::self = 0;

    >
    > > > // Example:

    >
    > > > #include <iostream>

    >
    > > > class foo : public singleton< foo >
    > > > {
    > > >         public:

    >
    > > >         void bar( void ) const
    > > >         {
    > > >                 std::cout << "foo::bar( )" << std::endl;
    > > >         }

    >
    > > > };

    >
    > > > int main( void )
    > > > {
    > > >         try
    > > >         {
    > > >                 foo a;
    > > >                 foo::instance( ).bar( );
    > > >                 foo c; // Whoops!
    > > >                 foo::instance( ).bar( );
    > > >         }
    > > >         catch( std::exception const& error )
    > > >         {
    > > >                 std::cerr << error.what( ) << std::endl;
    > > >         }

    >
    > > > }

    >
    > > > </code>

    >
    > > > The beauty of the design is that it allows the user to decide how to
    > > > allocate and initialize the derived class; it's sole purpose is to
    > > > make sure that multiple instances aren't created. Best of all, it's
    > > > completely generic!

    >
    > > > Cheers.

    >
    > > Looks as beautiful like any other reinvented square wheel. The
    > > requirements seem to be that such code must work:

    >
    > >  int main( void )
    > >  {
    > >      {
    > >          foo a;
    > >          foo::instance( ).bar( );
    > >      }
    > >      foo c; // Second singleton and *NO* Whoops
    > >      foo::instance( ).bar( );
    > >  }

    >
    > > Not sure why someone needs to have global state? Typical example of
    > > singletons is a logger. Huh? So ... OK. What if i need to have
    > > separate logs from different modules? I will then need new class for
    > > each log to have separate singleton logger for each module? Nonsense.

    >
    > > What if i need to have separate logs from different threads? Then that
    > > Logger::instance() should give me "different" singletons based on
    > > thread ID? Huh? Why it can't just be debugging::log() and where it
    > > logs is its internal business, no global state no nothing?

    >
    > > As for your code ... same thing with 10-12 lines instead of 70-80:

    >
    > >  #include <iostream>
    > >  namespace foo
    > >  {
    > >      void bar()
    > >      {
    > >          std::cout << "foo::bar()" << std::endl;
    > >      }
    > >  }

    >
    > >  int main()
    > >  {
    > >      foo::bar();
    > >  }

    >
    > > Things that contain nothing are not worth allocating or initializing.

    >
    > So...your point is that you hate the singleton pattern? Got it. I hate
    > it when people post snarky comments for no apparent reason,
    > personally. To each his (and her) own, I guess.


    Did i really insult you somewhere? Sorry then. I thought i posted
    reasons. I do not dislike something blindly. I have met them more than
    anyone deserves, and i have learned all possible and impossible ways
    how to deal with them. One-size-fits-all solutions are usually wrong
    so don't be insulted if yours is not exception.

    Why the problem with singletons is not so apparent? What is the
    difference between calling "globalVariable.doSomething()" and
    "SingletonClass::instance().doSomething()" (other than some extra
    letters to type on second case)? Both are tight coupling with global
    state only semantics are different. Sometimes it is not worth to avoid
    tight coupling between close classes but singleton is far and global.

    The problem is not only tight coupling between distant things but that
    such coupling is hidden within code (call site).

    One often named purpose of singletons is that these limit the count of
    how many instances there may be simultaneously (1 on case of
    singleton). That sounds like responsibility of owners of objects to
    limit number of simultaneous instances. Oh yes, global state does not
    have owners, it is self-owned.

    Also why only one instance? Who knows. "Pragmatic" reasons like "There
    was only one window/database/display/player/client/user/account/store/
    harddrive/configuration when we started with that application, so we
    decided to carve it into rock in most hard way to modify." Mono-media.

    Finally massive dependency on global state makes it impossible to rely
    on unit tests. I can not imagine large project without even larger
    amount of unit tests. Global state carries on behind scenes and so
    unit tests may pass (or fail) just because of order in what these were
    ran.

    These are not apparent reasons? Imagine 25 man-years that was put into
    C++ project. Result was with half of classes singletons (with
    similarly various "solutions" and "purposes" and "pragmatic reasons").
    Someone was paying lot of money for these 25 man-years so it was
    like ... desirable thing for him. Original global-state-lover
    architects did run far away because quite non-ambitious and reasonable
    change requests are near-impossible to fulfill. How to explain why
    what he has now is so costly to extend or maintain?

    So ... nothing personal, sebastian, but yes i dislike singletons. For
    good reasons.
     
    Öö Tiib, Jul 5, 2010
    #10
  11. Pallav singh

    James Kanze Guest

    On Jul 5, 12:31 am, Öö Tiib <> wrote:
    > On 4 juuli, 23:58, sebastian <> wrote:


    [...]
    > Looks as beautiful like any other reinvented square wheel. The
    > requirements seem to be that such code must work:


    > int main( void )
    > {
    > {
    > foo a;
    > foo::instance( ).bar( );
    > }
    > foo c; // Second singleton and *NO* Whoops
    > foo::instance( ).bar( );
    > }


    > Not sure why someone needs to have global state? Typical
    > example of singletons is a logger. Huh? So ... OK. What if
    > i need to have separate logs from different modules? I will
    > then need new class for each log to have separate singleton
    > logger for each module? Nonsense.


    So your log manager is a singleton. Somewhere, there must be
    a single bit of code which reads the configuration file for the
    log.

    Similarly, the configuration manager is a singleton. As is the
    code which captures the command line and its options. In
    a multithreaded application, the thread manager (which ensures
    e.g. a clean shutdown) must be a singleton.

    > What if i need to have separate logs from different threads?
    > Then that Logger::instance() should give me "different"
    > singletons based on thread ID? Huh? Why it can't just be
    > debugging::log() and where it logs is its internal business,
    > no global state no nothing?


    Huh? What is debugging::log()? (The syntax suggests a static
    class member. A class instance function, in sum. So that its
    data is a "singleton".)

    --
    James Kanze
     
    James Kanze, Jul 5, 2010
    #11
  12. Pallav singh

    James Kanze Guest

    On Jul 5, 2:36 pm, Öö Tiib <> wrote:
    > On 5 juuli, 05:48, sebastian <> wrote:


    [...]
    > Why the problem with singletons is not so apparent? What is
    > the difference between calling "globalVariable.doSomething()"
    > and "SingletonClass::instance().doSomething()" (other than
    > some extra letters to type on second case)? Both are tight
    > coupling with global state only semantics are different.
    > Sometimes it is not worth to avoid tight coupling between
    > close classes but singleton is far and global.


    > The problem is not only tight coupling between distant things
    > but that such coupling is hidden within code (call site).


    > One often named purpose of singletons is that these limit the
    > count of how many instances there may be simultaneously (1 on
    > case of singleton). That sounds like responsibility of owners
    > of objects to limit number of simultaneous instances. Oh yes,
    > global state does not have owners, it is self-owned.


    > Also why only one instance? Who knows. "Pragmatic" reasons
    > like "There was only one
    > window/database/display/player/client/user/account/store/
    > harddrive/configuration when we started with that application,
    > so we decided to carve it into rock in most hard way to
    > modify." Mono-media.


    I think there is some confusion about what is meant by
    a singleton. A singleton is a class which can only be
    instantiated once, regardless of how it is implemented. In C++,
    the most frequently cited idiom handles order of
    initialization (and is incredibly verbose), but that's
    a secondary aspect.

    Secondly, if the fact that a class can only have one instance is
    a fundamental invariant of the class, it makes more sense for
    the class itself to ensure this than for it to count on the
    client not making mistakes.

    Finally, the amount of coupling is to a large degree independant
    of whether something is a singleton or not. Arguably, there's
    even more coupling if you're passing a pointer to Log into every
    function in the application. And in my experience, most
    singletons are either static members, or are found in an unnamed
    namespace.

    In the end, the only real arguments against singletons are that
    1) they are often abused (but then, so are a lot of other
    things), and 2) the usual syntax is excessively verbose (but
    that's easy to fix---just use a lighter syntax).

    --
    James Kanze
     
    James Kanze, Jul 5, 2010
    #12
  13. Pallav singh

    Öö Tiib Guest

    On 5 juuli, 17:38, James Kanze <> wrote:
    > On Jul 5, 12:31 am, Öö Tiib <> wrote:
    >
    > > On 4 juuli, 23:58, sebastian <> wrote:

    >
    >     [...]
    >
    >
    >
    > > Looks as beautiful like any other reinvented square wheel. The
    > > requirements seem to be that such code must work:
    > >  int main( void )
    > >  {
    > >      {
    > >          foo a;
    > >          foo::instance( ).bar( );
    > >      }
    > >      foo c; // Second singleton and *NO* Whoops
    > >      foo::instance( ).bar( );
    > >  }
    > > Not sure why someone needs to have global state? Typical
    > > example of singletons is a logger. Huh? So ... OK. What if
    > > i need to have separate logs from different modules? I will
    > > then need new class for each log to have separate singleton
    > > logger for each module? Nonsense.

    >
    > So your log manager is a singleton.  Somewhere, there must be
    > a single bit of code which reads the configuration file for the
    > log.


    I am not saying there may not be single instances of something. I am
    saying that these should not be in some global state, so there is
    danger to produce multiple by mistake or copy it and so it has to be
    prevented by singleton pattern. Singular state is perfectly normal.
    Where it is needed hide it into implementation to keep interface
    laconic. That log configuration should be internal property of logging
    framework and not some global self-owned state for anyone to ask
    instance() for. Not even as private static member. Translation unit
    local is perfect. Then it is function debugging::log() that consults
    with private log manager (if there exist such) to find out where it
    logs and how (if that differs) and not everyone typing nonsense like:

    debugging::LogManager::instance().produceLogger().doYourTrick("bla
    bla");

    > Similarly, the configuration manager is a singleton.


    Depends what it manages. If "configuration" of dynamically loadable
    modules then such thing must be there, but i would call it
    "application" object (or its "configuration" member). If these are
    module settings then these belong to each module. It is sad that C++
    does not contain concept of dynamically loadable modules.

    > As is the code which captures the command line and its options.  


    Command line is passed to main() and so main() passes it to some
    singleton? Why it should be a singleton? These are command line
    arguments for something that will be further called by main(). Why
    there must be a global singleton that holds its options? However that
    does not worry me, after all there are very few things that directly
    depend on command line and that command line does not likely change
    during program run.

    > In a multithreaded application, the thread manager (which ensures
    > e.g. a clean shutdown) must be a singleton.


    At the moment yes, application (or some framework that it uses) has to
    orchestrate shutdown itself. Again, when i do not get rid of single
    things then i do not like "ShutDownManager::instance().doIt()". I
    prefer to have shutDown() function. If nothing else then faking it for
    a unit test is lot cheaper.

    > > What if i need to have separate logs from different threads?
    > > Then that Logger::instance() should give me "different"
    > > singletons based on thread ID? Huh? Why it can't just be
    > > debugging::log() and where it logs is its internal business,
    > > no global state no nothing?

    >
    > Huh?  What is debugging::log()?  (The syntax suggests a static
    > class member.  A class instance function, in sum.  So that its
    > data is a "singleton".)


    No, i meant a namespace, sorry for not being clear there.
    debugging::log() like std::sort(). Actually i suggest to wrap logging
    into macro anyway. Some useful information like file/function/
    linenumber are impossible to gather in a generic way without macros
    involved.
     
    Öö Tiib, Jul 5, 2010
    #13
  14. Pallav singh

    Öö Tiib Guest

    On 5 juuli, 19:57, James Kanze <> wrote:
    >
    > In the end, the only real arguments against singletons are that
    > 1) they are often abused (but then, so are a lot of other
    > things), and 2) the usual syntax is excessively verbose (but
    > that's easy to fix---just use a lighter syntax).


    Yes, exactly. Nothing suggests to use:

    SingletonFactory::instance().giveCordStringTyer().tie( cordString );

    Use good syntax:

    tie( cordString );
     
    Öö Tiib, Jul 5, 2010
    #14
  15. Pallav singh

    James Kanze Guest

    On Jul 5, 6:20 pm, Öö Tiib <> wrote:
    > On 5 juuli, 19:57, James Kanze <> wrote:


    > > In the end, the only real arguments against singletons are that
    > > 1) they are often abused (but then, so are a lot of other
    > > things), and 2) the usual syntax is excessively verbose (but
    > > that's easy to fix---just use a lighter syntax).


    > Yes, exactly. Nothing suggests to use:
    >
    > SingletonFactory::instance().giveCordStringTyer().tie( cordString );


    > Use good syntax:


    > tie( cordString );


    You reduce coupling somewhat by grouping functions in classes.
    (If nothing else, they don't invade global namespace.) Still,
    something like:
    CommandLine::parse(argc, argv);
    is still a lot less verbose than:
    CommandLine::instance().parse(argc, argv);

    I've recently remodeled most of my singletons to use this
    syntax. In some cases, there may be a more classical singleton
    behind the scenes (in order to resolve order of initialization
    issues, for example), but there's no point in burdening the
    client code with such details.

    I haven't worked out a way to do this with templates, and
    I don't think I'm going to bother. While I don't have the
    horror of singletons that some do, there's not something that
    I use frequently enough to justify developing a complex template
    for them.

    --
    James Kanze
     
    James Kanze, Jul 5, 2010
    #15
  16. Pallav singh

    James Kanze Guest

    On Jul 5, 6:05 pm, Öö Tiib <> wrote:
    > On 5 juuli, 17:38, James Kanze <> wrote:
    > > On Jul 5, 12:31 am, Öö Tiib <> wrote:


    > > > On 4 juuli, 23:58, sebastian <> wrote:


    > > [...]


    > > > Looks as beautiful like any other reinvented square wheel.
    > > > The requirements seem to be that such code must work:
    > > > int main( void )
    > > > {
    > > > {
    > > > foo a;
    > > > foo::instance( ).bar( );
    > > > }
    > > > foo c; // Second singleton and *NO* Whoops
    > > > foo::instance( ).bar( );
    > > > }
    > > > Not sure why someone needs to have global state? Typical
    > > > example of singletons is a logger. Huh? So ... OK. What if
    > > > i need to have separate logs from different modules?
    > > > I will then need new class for each log to have separate
    > > > singleton logger for each module? Nonsense.


    > > So your log manager is a singleton. Somewhere, there must
    > > be a single bit of code which reads the configuration file
    > > for the log.


    > I am not saying there may not be single instances of
    > something. I am saying that these should not be in some global
    > state,


    It's not "global" state:).

    > so there is danger to produce multiple by mistake or
    > copy it and so it has to be prevented by singleton pattern.
    > Singular state is perfectly normal. Where it is needed hide
    > it into implementation to keep interface laconic. That log
    > configuration should be internal property of logging framework
    > and not some global self-owned state for anyone to ask
    > instance() for. Not even as private static member. Translation
    > unit local is perfect. Then it is function debugging::log()
    > that consults with private log manager (if there exist such)
    > to find out where it logs and how (if that differs) and not
    > everyone typing nonsense like:


    > debugging::LogManager::instance().produceLogger().doYourTrick("bla
    > bla");


    Well, logging is a very special case. Independantly of the
    singleton argument, you need to keep the invocations as succinct
    as possible, and the test whether the given level is active or
    not as fast as possible. This suggests macros (which also allow
    automatic insertion of __LINE__ and __FILE__), and some sort of
    static variables, rather than a test in an instance functions.
    I'll usually use something like:

    extern LogStream* logOutput[];

    #define LOG(n) logOutput[n] != NULL
    && *logOutput[n] << __FILE__ << ":" << __LINE__

    And of course, LogStream can't be a singleton. But the code
    which initializes logOutput might be, especially if it has to
    wait for external events and possibly update the logOutput
    table. And in very large applications, there's likely to be
    a logOutput[] instance per subsystem, wrapped in a class, with
    a constructor which registers it with a central log manager,
    which reads the log configuration when instructed to (since you
    can't necessarily shut down the application just to change the
    configuration of its log). In such cases, log manager is likely
    to be very much like a classic singleton (if only to handle
    order of initialization issues).

    > > Similarly, the configuration manager is a singleton.


    > Depends what it manages. If "configuration" of dynamically
    > loadable modules then such thing must be there, but i would
    > call it "application" object (or its "configuration" member).
    > If these are module settings then these belong to each module.
    > It is sad that C++ does not contain concept of dynamically
    > loadable modules.


    > > As is the code which captures the command line and its options.


    > Command line is passed to main() and so main() passes it to
    > some singleton? Why it should be a singleton?


    Because there can't be more than one command line. Options have
    to register before main is called (from the constructor of
    a static object), so you need something to handle the order of
    initialization issues.

    > These are command line arguments for something that will be
    > further called by main(). Why there must be a global singleton
    > that holds its options?


    Because no one component is interested in all of the options.

    > However that does not worry me, after all there are very few
    > things that directly depend on command line and that command
    > line does not likely change during program run.


    Not once it has been parsed. But Option enroles with the
    CommandLine class, so that it can correctly pick up options when
    it parses the command line.

    > > In a multithreaded application, the thread manager (which
    > > ensures e.g. a clean shutdown) must be a singleton.


    > At the moment yes, application (or some framework that it
    > uses) has to orchestrate shutdown itself. Again, when i do not
    > get rid of single things then i do not like
    > "ShutDownManager::instance().doIt()". I prefer to have
    > shutDown() function. If nothing else then faking it for a unit
    > test is lot cheaper.


    The main argument against this solution is that it doesn't work.
    The task manager has to know about all of the tasks, so that it
    can signal them in case of a shutdown request, then wait until
    they've finished.

    (Thinking about it, this seems to be a common theme of
    singletons. The have to know about all of the instances of
    something else: threads, temporary files, etc.)

    > > > What if i need to have separate logs from different
    > > > threads? Then that Logger::instance() should give me
    > > > "different" singletons based on thread ID? Huh? Why it
    > > > can't just be debugging::log() and where it logs is its
    > > > internal business, no global state no nothing?


    > > Huh? What is debugging::log()? (The syntax suggests
    > > a static class member. A class instance function, in sum.
    > > So that its data is a "singleton".)

    >
    > No, i meant a namespace, sorry for not being clear there.
    > debugging::log() like std::sort(). Actually i suggest to wrap
    > logging into macro anyway. Some useful information like
    > file/function/ linenumber are impossible to gather in
    > a generic way without macros involved.


    Yes. More generally, however, when single instances of data are
    involved, I prefer to wrap in a class than in a namespace. Once
    I've defined the class, no one else can get at the data.

    --
    James Kanze
     
    James Kanze, Jul 5, 2010
    #16
  17. Pallav singh

    Öö Tiib Guest

    On 5 juuli, 21:06, James Kanze <> wrote:
    > On Jul 5, 6:05 pm, Öö Tiib <> wrote:
    >
    >
    >
    > > On 5 juuli, 17:38, James Kanze <> wrote:
    > > > On Jul 5, 12:31 am, Öö Tiib <> wrote:
    > > > > Not sure why someone needs to have global state? Typical
    > > > > example of singletons is a logger. Huh? So ... OK. What if
    > > > > i need to have separate logs from different modules?
    > > > > I will then need new class for each log to have separate
    > > > > singleton logger for each module? Nonsense.
    > > > So your log manager is a singleton.  Somewhere, there must
    > > > be a single bit of code which reads the configuration file
    > > > for the log.

    > > I am not saying there may not be single instances of
    > > something. I am saying that these should not be in some global
    > > state,

    >
    > It's not "global" state:).


    Ok, about hidden implementation details i do not usually complain.
    Whatever is elegant to get interface contract fulfilled. If it is
    singleton most fitting there then so be it.

    [...]

    > Well, logging is a very special case.  


    Yes, logging is most valuable debugging/issue resolving tool.
    Especially when there are difficulties to debug, like with some
    embedded systems. I did bring it in because it is typical thing that i
    have heard is a "natural singleton". Seems that we agree there,
    natural interface for logging in C++ is a macro. Singletons interface
    does not pull the weight. Singleton may be again some behind scenes
    implementation detail.

    What I hate is when singleton is sort of replacement for a global
    variable. That is the cheat how that pattern is often abused.

    > > > As is the code which captures the command line and its options.

    > > Command line is passed to main() and so main() passes it to
    > > some singleton? Why it should be a singleton?

    >
    > Because there can't be more than one command line.  Options have
    > to register before main is called (from the constructor of
    > a static object), so you need something to handle the order of
    > initialization issues.
    >
    > > These are command line arguments for something that will be
    > > further called by main(). Why there must be a global singleton
    > > that holds its options?

    >
    > Because no one component is interested in all of the options.


    OK, may be it is reasonable. However such options may be passed to
    component run-time as well? What is the difference if the source is
    command line or some user command to change them later, run-time?

    > > However that does not worry me, after all there are very few
    > > things that directly depend on command line and that command
    > > line does not likely change during program run.

    >
    > Not once it has been parsed.  But Option enroles with the
    > CommandLine class, so that it can correctly pick up options when
    > it parses the command line.


    Ok, there is just one command line and pretending there may be several
    is pointless when there are no other sources of options.

    > > > In a multithreaded application, the thread manager (which
    > > > ensures e.g. a clean shutdown) must be a singleton.

    > > At the moment yes, application (or some framework that it
    > > uses) has to orchestrate shutdown itself. Again, when i do not
    > > get rid of single things then i do not like
    > > "ShutDownManager::instance().doIt()". I prefer to have
    > > shutDown() function. If nothing else then faking it for a unit
    > > test is lot cheaper.

    >
    > The main argument against this solution is that it doesn't work.
    > The task manager has to know about all of the tasks, so that it
    > can signal them in case of a shutdown request, then wait until
    > they've finished.


    To expose something to a function is actually as hard as to expose it
    to a class, isn't it? Ok, task manager. I do not still see why there
    must be a class for it.

    namespace taskmanager {
    void shutDown(); // shortest thing to say.
    // other operations with task manager.
    }

    It might be feels like C way of information hiding, but nameless
    namespaces are exactly for that ... like i understand the standard.
    Sure, it may be a class too.

    > (Thinking about it, this seems to be a common theme of
    > singletons.  The have to know about all of the instances of
    > something else: threads, temporary files, etc.)


    Yes. For example factories. I prefer factory functions when there are
    limits so creation (or destruction, or reusage) of something should
    not be made in usual ways. How a factory function achieves it is
    implementation detail. It may use real singletons that are defined in
    (nameless namespace in) translation unit that defines such factory
    function.

    Such design likely removes (or adds flexibility how to handle) the
    issues that may be with construction/destruction order of singletons.
    Namespace also naturally does not let any usual questions about
    classes (like what if i copy or derive from or use as member or
    delete) to be asked with straight face.
    [...]

    > Yes.  More generally, however, when single instances of data are
    > involved, I prefer to wrap in a class than in a namespace.  Once
    > I've defined the class, no one else can get at the data.


    I believe nameless namespace in a translation unit is deepest place
    where single instance of data can be hidden with C++. It may be is my
    allergic overreaction to widespread abuse of singletons, so i want to
    put them as far from global as possible. ;-)
     
    Öö Tiib, Jul 6, 2010
    #17
  18. Pallav singh

    James Kanze Guest

    On Jul 6, 1:21 am, Öö Tiib <> wrote:
    > On 5 juuli, 21:06, James Kanze <> wrote:
    > > On Jul 5, 6:05 pm, Öö Tiib <> wrote:


    [...]
    > > > > As is the code which captures the command line and its options.
    > > > Command line is passed to main() and so main() passes it to
    > > > some singleton? Why it should be a singleton?


    > > Because there can't be more than one command line. Options have
    > > to register before main is called (from the constructor of
    > > a static object), so you need something to handle the order of
    > > initialization issues.


    > > > These are command line arguments for something that will be
    > > > further called by main(). Why there must be a global singleton
    > > > that holds its options?


    > > Because no one component is interested in all of the options.


    > OK, may be it is reasonable. However such options may be passed to
    > component run-time as well? What is the difference if the source is
    > command line or some user command to change them later, run-time?


    If there is some user command to change them later, then they
    aren't command line options. Long running programs don't
    normally use command line options (other than the specify the
    configuration files); they use configuration files, and if the
    user can issue commands to modify the configuration on the fly,
    they probably rewrite the configuration file as well. Command
    line options are for short running programs, which do one thing
    and exit (like a compiler). My options are variables at
    namespace scope. Preferrably local to the module in which they
    are used. The constructor calls a function in CommandLine which
    enrols them.

    While convenient at some levels, this solution isn't perfect.
    You've still got to find all of those options when it comes to
    writing the man page or help text. But globally, I've found it
    very useful to be able to define an option in the module which
    uses it, without having to modify any central code which "knows"
    all of the options.

    > > > However that does not worry me, after all there are very few
    > > > things that directly depend on command line and that command
    > > > line does not likely change during program run.


    > > Not once it has been parsed. But Option enroles with the
    > > CommandLine class, so that it can correctly pick up options when
    > > it parses the command line.


    > Ok, there is just one command line and pretending there may be
    > several is pointless when there are no other sources of
    > options.


    Even when much of the configuration may come from
    a configuration file, it's useful to access it through a single
    co-ordinator. (I have, or maybe only had, code somewhere which
    does this. It's a singleton which maintains a list of
    configuration sources; when you ask it for a value, it goes
    through the list, returning the first it finds. First in the
    list is typically a collection of options, registered with the
    command line, followed by an object which reads environment
    variables, followed by one or more files, followed by an object
    which returns the defaults.)

    > > > > In a multithreaded application, the thread manager (which
    > > > > ensures e.g. a clean shutdown) must be a singleton.
    > > > At the moment yes, application (or some framework that it
    > > > uses) has to orchestrate shutdown itself. Again, when i do not
    > > > get rid of single things then i do not like
    > > > "ShutDownManager::instance().doIt()". I prefer to have
    > > > shutDown() function. If nothing else then faking it for a unit
    > > > test is lot cheaper.


    > > The main argument against this solution is that it doesn't work.
    > > The task manager has to know about all of the tasks, so that it
    > > can signal them in case of a shutdown request, then wait until
    > > they've finished.


    > To expose something to a function is actually as hard as to expose it
    > to a class, isn't it? Ok, task manager. I do not still see why there
    > must be a class for it.


    It needs to be a container, which can contain a variable number
    of entries. Thus, a class. You can use std::vector<Thread*> if
    you want, but in that case, you may still want to handle order
    of initialization issues, in order to allow threads to be
    started from the constructor of a static object. (Not usually
    a good idea, but there are probably cases where it is
    justified.)

    > namespace taskmanager {
    > void shutDown(); // shortest thing to say.
    > // other operations with task manager.
    > }


    And where do you put the data that taskmanager::shutDown needs
    to manipulate? Data which is also accessed each time you start
    a thread, etc.

    > It might be feels like C way of information hiding, but
    > nameless namespaces are exactly for that ... like i understand
    > the standard. Sure, it may be a class too.


    Unnamed namespaces are only accessible from the translation unit
    in which they occur. Something like a thread probably has
    a couple of different globally accessible functions; if it's in
    library code, each will be in a separate file.

    > > (Thinking about it, this seems to be a common theme of
    > > singletons. The have to know about all of the instances of
    > > something else: threads, temporary files, etc.)


    > Yes. For example factories. I prefer factory functions when
    > there are limits so creation (or destruction, or reusage) of
    > something should not be made in usual ways. How a factory
    > function achieves it is implementation detail. It may use real
    > singletons that are defined in (nameless namespace in)
    > translation unit that defines such factory function.


    The classical singleton is nothing more than a factory function.
    With the twist that it always returns the same instance, rather
    than a new one each time.

    > Such design likely removes (or adds flexibility how to handle) the
    > issues that may be with construction/destruction order of singletons.
    > Namespace also naturally does not let any usual questions about
    > classes (like what if i copy or derive from or use as member or
    > delete) to be asked with straight face.
    > [...]


    > > Yes. More generally, however, when single instances of data are
    > > involved, I prefer to wrap in a class than in a namespace. Once
    > > I've defined the class, no one else can get at the data.


    > I believe nameless namespace in a translation unit is deepest place
    > where single instance of data can be hidden with C++.


    It's too deep, since only the functions in that one translation
    unit can get too it. (Actually, it depends, and in cases where
    a helper class or helper functions are only needed in a single
    function, I'll put them in the unnamed namespace. I'm also
    fairly fond of using namespaces named XxxPrivate, defined in
    a local header which isn't exported.)

    --
    James Kanze
     
    James Kanze, Jul 6, 2010
    #18
  19. Pallav singh

    Jorgen Grahn Guest

    On Sun, 2010-07-04, Leigh Johnston wrote:
    > "Trifle Menot" <> wrote in message
    > news:eek:...
    >> On Sun, 4 Jul 2010 08:42:25 -0700 (PDT), Öö Tiib <> wrote:
    >>
    >>>Global state is bad design in all languages.

    >>
    >> Not for small programs where you're the sole author. Things should be
    >> as simple as possible.
    >>

    >
    > Size or number of developers are no excuse: bad habits are bad habits
    > period.


    I agree with you about size and number of people, but with him on "as
    simple as possible". I don't often use global state, but I think it's
    a valid design in some cases.

    (But people who use it should know about the pitfalls -- for example
    how often requirements change so what you believed was global no
    longer is, and how bloody hard it can be to rewrite code with global
    state.)

    /Jorgen

    --
    // Jorgen Grahn <grahn@ Oo o. . .
    \X/ snipabacken.se> O o .
     
    Jorgen Grahn, Jul 6, 2010
    #19
  20. Pallav singh

    Öö Tiib Guest

    On 6 juuli, 16:43, James Kanze <> wrote:
    > On Jul 6, 1:21 am, Öö Tiib <> wrote:
    >
    > > On 5 juuli, 21:06, James Kanze <> wrote:
    > > > On Jul 5, 6:05 pm, Öö Tiib <> wrote:

      [...]

    > If there is some user command to change them later, then they
    > aren't command line options.  Long running programs don't
    > normally use command line options (other than the specify the
    > configuration files); they use configuration files, and if the
    > user can issue commands to modify the configuration on the fly,
    > they probably rewrite the configuration file as well.  Command
    > line options are for short running programs, which do one thing
    > and exit (like a compiler).  My options are variables at
    > namespace scope.  Preferrably local to the module in which they
    > are used.  The constructor calls a function in CommandLine which
    > enrols them.
    >
    > While convenient at some levels, this solution isn't perfect.
    > You've still got to find all of those options when it comes to
    > writing the man page or help text.  But globally, I've found it
    > very useful to be able to define an option in the module which
    > uses it, without having to modify any central code which "knows"
    > all of the options.


    Ok, i have used a bit different way. Each option is mapped to command
    (function or functor). As options are parsed the commands are
    executed. That results with command line being parsed, passed around
    and forgotten immediately. Same commands can be executed later by
    other means for some reason an option has to be changed. At same place
    where commands are there may be little help texts and hints if needed.
    At simplest case it is static constant array in some nameless
    namespace.

    Probably it is because i like somewhat extended interface for command
    line application ...
    If some mandatory option was missing from command line then program
    may ask for it (instead of telling it was error).
    When no options were given at all it may enter into interactive mode
    (instead of telling about typical usage with few lines).
    Such twists are not too uncommon and make testing it simpler.

    > > Ok, there is just one command line and pretending there may be
    > > several is pointless when there are no other sources of
    > > options.

    >
    > Even when much of the configuration may come from
    > a configuration file, it's useful to access it through a single
    > co-ordinator.  (I have, or maybe only had, code somewhere which
    > does this.  It's a singleton which maintains a list of
    > configuration sources; when you ask it for a value, it goes
    > through the list, returning the first it finds.  First in the
    > list is typically a collection of options, registered with the
    > command line, followed by an object which reads environment
    > variables, followed by one or more files, followed by an object
    > which returns the defaults.)


    It is difficult to achieve if there are components written by third
    parties. It is bit easier to equip them with an interface how to add
    command line commands. If keeping handling configuration files must be
    centralized then i prefer to provide a simplest interface:

    namespace configuration
    {
    void read( ModuleID id, vector<char>& bytes );
    void write( ModuleID id, vector<char> const& bytes );
    }

    Simplest interfaces are simplest to extend. I may handle it as ini or
    xml file, for me it is set of bytes i preserve in exact form. When all
    modules are mine then of course it is cheaper to have some extended
    interface so each configurable value can retrieved from common tree
    (or its branch).

    > > > > > In a multithreaded application, the thread manager (which
    > > > > > ensures e.g. a clean shutdown) must be a singleton.
    > > > > At the moment yes, application (or some framework that it
    > > > > uses) has to orchestrate shutdown itself. Again, when i do not
    > > > > get rid of single things then i do not like
    > > > > "ShutDownManager::instance().doIt()". I prefer to have
    > > > > shutDown() function. If nothing else then faking it for a unit
    > > > > test is lot cheaper.
    > > > The main argument against this solution is that it doesn't work.
    > > > The task manager has to know about all of the tasks, so that it
    > > > can signal them in case of a shutdown request, then wait until
    > > > they've finished.

    > > To expose something to a function is actually as hard as to expose it
    > > to a class, isn't it? Ok, task manager. I do not still see why there
    > > must be a class for it.

    >
    > It needs to be a container, which can contain a variable number
    > of entries.  Thus, a class.  You can use std::vector<Thread*> if
    > you want, but in that case, you may still want to handle order
    > of initialization issues, in order to allow threads to be
    > started from the constructor of a static object.  (Not usually
    > a good idea, but there are probably cases where it is
    > justified.)


    There are so many possible ways how to handle and manage concurrency.
    I think there are at least 4 major ways plus endless subtypes. Some,
    (like OpenMP) make it business of implementation others deal with
    threads very closely and explicitly. I do not think that any of them
    does start threads from constructors of static objects, but who knows.

    > >  namespace taskmanager {
    > >      void shutDown(); // shortest thing to say.
    > >      // other operations with task manager.
    > >  }

    >
    > And where do you put the data that taskmanager::shutDown needs
    > to manipulate?  Data which is also accessed each time you start
    > a thread, etc.


    Why not in some personal vector of taskmanager? Everyone has to give
    their tasks to taskmanager without knowing how many threads for the
    job there is. Is it some other model of concurrency? Yes, some things
    may need specific thread. For example OpenGL is AFAIK implemented so
    that you can draw to one display from only one thread and no other
    thread. However presence of such threads may be also consulted (with
    some special function) to taskmanager.

    > > It might be feels like C way of information hiding, but
    > > nameless namespaces are exactly for that ... like i understand
    > > the standard.  Sure, it may be a class too.

    >
    > Unnamed namespaces are only accessible from the translation unit
    > in which they occur.  Something like a thread probably has
    > a couple of different globally accessible functions; if it's in
    > library code, each will be in a separate file.


    Thread is not like object for me. It is more like running function
    (activity). Threads usually communicate with messages or signals.
    Basic functionality function of receiving messages and accepting jobs
    to do and reporting back about problems may be same for all threads.
    On that case also the place from where they get their tasks may be
    centralized and be located at same place the function is implemented.

    The tasks that thread does may have some other mechanics for canceling
    them on half run, for example they may get some signal interface to
    attach and observe. That really needs whole separate newsgroup about
    how to implement concurrency in C++; there probably are some in
    usenet.

    > > > (Thinking about it, this seems to be a common theme of
    > > > singletons.  The have to know about all of the instances of
    > > > something else: threads, temporary files, etc.)

    > > Yes. For example factories. I prefer factory functions when
    > > there are limits so creation (or destruction, or reusage) of
    > > something should not be made in usual ways. How a factory
    > > function achieves it is implementation detail. It may use real
    > > singletons that are defined in (nameless namespace in)
    > > translation unit that defines such factory function.

    >
    > The classical singleton is nothing more than a factory function.
    > With the twist that it always returns the same instance, rather
    > than a new one each time.


    I believe it is bad twist and does not fit too well into C++ where you
    may have free functions. Every time i see one it feels like
    "std::sorter::instance().sort(from, to)". When it is surely same
    object of whose member functions i call then i prefer to not have that
    object on table at all. With that object i may anyway do nothing but
    call its member functions. So ... plain set of functions is fine.
    There may be case when i need to extract an interface from it to pass
    into somewhere that expects such interface. Then i prefer to have
    function that provides such interface, why should caller know if it is
    whole singleton itself or some data member of it? If there are chances
    that there may be more instances than one then i see reason for
    factory function. However "instance()" is a bad name for a factory
    function.

    > > Such design likely removes (or adds flexibility how to handle) the
    > > issues that may be with construction/destruction order of singletons.
    > > Namespace also naturally does not let any usual questions about
    > > classes (like what if i copy or derive from or use as member or
    > > delete) to be asked with straight face.
    > >  [...]
    > > > Yes.  More generally, however, when single instances of data are
    > > > involved, I prefer to wrap in a class than in a namespace.  Once
    > > > I've defined the class, no one else can get at the data.

    > > I believe nameless namespace in a translation unit is deepest place
    > > where single instance of data can be hidden with C++.

    >
    > It's too deep, since only the functions in that one translation
    > unit can get too it.  (Actually, it depends, and in cases where
    > a helper class or helper functions are only needed in a single
    > function, I'll put them in the unnamed namespace.  I'm also
    > fairly fond of using namespaces named XxxPrivate, defined in
    > a local header which isn't exported.)


    Usually it is not too deep. Then i win. Often singleton was there
    before, hiding it away is expensive and i likely have more packing
    issues to handle. Then it won. For now. :D But namespace is seriously
    best singleton interface since i can have such separate ("internal"
    like in C#) interface in other header, whole namespace does not have
    to be declared in one header unlike a class.
     
    Öö Tiib, Jul 6, 2010
    #20
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Nathac
    Replies:
    0
    Views:
    355
    Nathac
    Dec 22, 2006
  2. design
    Replies:
    1
    Views:
    325
    =?ISO-8859-1?Q?Arne_Vajh=F8j?=
    Jan 10, 2007
  3. Tiwkiz
    Replies:
    1
    Views:
    375
    Daniel Dyer
    Jan 11, 2007
  4. MaxMax
    Replies:
    4
    Views:
    361
    MaxMax
    Oct 25, 2005
  5. sebastian
    Replies:
    1
    Views:
    405
    sebastian
    Jul 5, 2010
Loading...

Share This Page