where does singleton come to play?

Started by
18 comments, last by nilkn 18 years, 10 months ago
Quote:Original post by derek7
Quote:template<class T>
class singleton
{
public:
static T& getInstance()
{
if(!instance)
{
instance = new T;
}
return *instance;
}
private:
static T* instance;
};


template<class T>
T* singleton<T>::instance = 0;


what is "T* singleton<T>::instance = 0;"?
it is a function? because have return type T*.
it is a memeber of data? because ::instance is static T* instance;


it is not a function, it just like the format of declare an object
T is a template class.
every static instance need to redeclare outside the class
tototam
Advertisement
Apart from controlling that there's only one instance of the class, another important property of a singleton is that you can be sure that it's instantiated when you're using it. This is not the case when it comes to static classes. If you use the members of one static class from the constructor of another you might be in trouble since you're not sure of the order in which they're created.
Singeltons are one of the most misused patterns I've ever seen. Singeltons are almost never appropriate the way most people use them--basically, as a global access point.
Quote:Original post by CraZeE
i'm not really contributing to the topic but i DO have a related question. Been using singleton's on several occasions and they were handy. But it just crossed my mind that although instantiation is only ONCE, how do you prevent accidental deletion?

a singleton instantiates itself on first reference: easy to do by protecting the constructors and allowing a GetInstance-kind of function. But by that, you will get back a pointer.

What is to stop someone from accidentally deleting the pointer? I personally use a specific shutdown function to force termination of a singleton, but i neva actually tried deleting it directly (mainly coz i created the functon for a purpose :P ). Can accidental 'delete' be prevented?


Nitage gave a good answer and implementation, but I thought I'd offer up another simpler one that loses the if statement, and the dynamic allocation. Keep in mind that every example posted so far (including this one) does not take up the issue of thread safe Singletons.

class Singleton{public:   static Singleton &instance(void)   {      static Singleton rv;      return rv;   }};


(I also agree with the above poster)
--Michael Fawcett
It's generally a bad idea to use singletons all over the place in your game. For instance, if your game looks like this: DisplayManager Singleton, Renderer Singleton, ResourceManager Singleton, LevelMesh Singleton, PartitionManager Singleton, Profiler Singleton, Server Singleton, etc etc.. If your game looks like this, you are misusing and abusing the singleton pattern.

For one, it's going to cause headaches and be a nightmare to fix all the bugs that happen on destruction, since the order of destruction is undefined for global objects (ie, the LevelMesh getting destroyed before the Renderer, or the ResourceManager before the Renderer, etc). Aside from that, its terrible OO programming practice. It's absolutely no better than the DirectX Samples where they put every variable used in the program as a global at the top of main.cpp.

It's perfectly possible and even desirable to create a game engine that does not use even one singleton. It will give you a good practice in object oriented design and force you to make use of some other good design patterns. And, you will find that your engine is much more robust and flexible with a stronger sense of encapsulation and abstraction.
You also need to explicitly destroy the pointer in the example I gave, you'd have to wrap it in a smart pointer for it to be automatically destroyed.

Singletons are overused, but that doesn't mean that they don't have uses.

I'm currently only using one for my debugging system (which handles logging etc.).

Every piece of code needs access to it and there should only ever be one instance, so it's an excellent place to use it.

Making things like your main application class a singleton is a bad idea. You may only ever want one intance, but it's unlikely that you want every piece of code to have access to it.

I used to have alot of singletons in my engine (it WAS based on enginuity) until I realized that there's almost always a better way to solve the problems I had than to use a singleton. Right now I only use a singleton in my log system, and that's about to change.
Quote:Original post by Nitage
You also need to explicitly destroy the pointer in the example I gave, you'd have to wrap it in a smart pointer for it to be automatically destroyed.

Singletons are overused, but that doesn't mean that they don't have uses.

I'm currently only using one for my debugging system (which handles logging etc.).

Every piece of code needs access to it and there should only ever be one instance, so it's an excellent place to use it.

Making things like your main application class a singleton is a bad idea. You may only ever want one intance, but it's unlikely that you want every piece of code to have access to it.

Most of the time singletons can be replaced with just a normal class with one instance; actually, I can't think of any situation in which a singleton would be better. The bad things about singletons, and global data in general, is that their not explicit, and in some cases, practically hidden. While this might not be that bad in your personal projects, it would be a mess for pretty much anyone else, or even yourself after 2 months, not to mention the mess that it would cause when you try and reuse some of it. While using a singelton for a logging subsystem might look okay, what happens if you want to have two logs? Instead, a simple Log class would probably be best, or even better, you could just pass around a std::ostream and not even bother making a class.

Here's some advice if you still need to use singletons: isolate their use to the highest-level game-specific code in your game.

Finally, some of the best advice I can give is to follow the unix philosophy: write components that do one thing and do it well.

[Edited by - bytecoder on June 13, 2005 1:37:50 PM]
Quote:Original post by Omaha
I really see no benefit to singletons except in entirely object-oriented languages like Java, where in, for instance, a server environment, it's likely that multiple clients may be using the same virtual machine and need access to the same object, which must only be instantiated once. (And in this case it can be very useful; we use it at work all the time.)

The purpose of a singleton is to ensure that an object is instantiated once and only once. This is usually because the object represents something that logically only exists once, like the video subsystem or (I still gag thinking of things like "CGameEngine") God forbid the engine.

However, in that instance I think that you're actually misusing the purpose of a class. C++ classes are very good for some things: encapsulation, inheritance, polymorphism, etc. If you're going to use a singleton, then you're not going to be using inheritance, you're not really encapsulating much because in essence you just have a glorified struct that is only being created once, and you can't very well use polymorphism if you don't inherit. So why even bother creating a whole class for something that will be instantiated once?


I don't want to be rude, nor I want to be disrepectful, but I believe you completly missed the whole point of singleton.

Have a look to Loki's singleton - you'll probably learn a lot about them.

The singleton The main thing about a singleton is not that you create only one instance of a particular object, but that you control how you gain access to this instance.

Regards,
Singletons - why they're potentially bad.

Summarization:

1. Use singletons only when all three of the following are true:

a. Will every application use this class exactly the same way? (exactly is the key word)
b. Will every application ever need only one instance of this class? (ever and one are the key words)
c. Should the clients of this class be unaware of the application they are part of?

2. Singletons provide too much information to their clients: the clients now know how to get instances of the Singleton.

3. Clients using a singleton provider's instanciation routine must know which provider they're dealing with in the case of an inheritance hierarchy (for example, OpenGL and Direct3D implementations of a Renderer singleton; client code must know whether it's using the OpenGL or Direct3D version).

This topic is closed to new replies.

Advertisement