tags:

views:

237

answers:

6

I need to store a bunch of variables that need to be accessed globally and I'm wondering if a singleton pattern would be applicable. From the examples I've seen, a singleton pattern is just a static class that can't be inherited. But the examples I've seen are overly complex for my needs. What would be the very simplest singleton class? Couldn't I just make a static, sealed class with some variables inside?

+1  A: 

A Singleton isn't just a static class that can't be inherited. It's a regular class that can be instantiated only once, with everybody sharing that single instance (and making it thread safe is even more work).

The typical .NET code for a Singleton looks something like the following. This is a quick example, and not by any means the best implementation or thread-safe code:

public sealed class Singleton
{
    Singleton _instance = null;

    public Singleton Instance
    {
        get
        {
            if(_instance == null)
                _instance = new Singleton();

            return _instance;
        }
    }

    // Default private constructor so only we can instanctiate
    private Singleton() { }

    // Default private static constructor
    private static Singleton() { }
}

If you're going to go down the path you're thinking, a static sealed class will work just fine.

Justin Niessner
I think you need to revise that code somewhat - and unless you're careful in the revision, it won't be thread-safe. However, making it thread-safe is really pretty easy.
Jon Skeet
@Jon I wasn't going for the thread-safe version here. Quick example. I know one way to make it thread-safe, but I'd be interested to know the other revisions (just out of curiosity).
Justin Niessner
+15  A: 

Typically a singleton isn't a static class - a singleton will give you a single instance of a class.

I don't know what examples you've seen, but usually the singleton pattern can be really simple in C#:

public sealed class Singleton
{
    private static readonly Singleton instance = new Singleton();
    private static Singleton() {} // Make sure it's truly lazy
    private Singleton() {} // Prevent instantiation outside

    public static Singleton Instance { get { return instance; }
}

That's not difficult.

The advantage of a singleton over static members is that the class can implement interfaces etc. Sometimes that's useful - but other times, static members would indeed do just as well. Additionally, it's usually easier to move from a singleton to a non-singleton later, e.g. passing in the singleton as a "configuration" object to dependency classes, rather than those dependency classes making direct static calls.

Personally I'd try to avoid using singletons where possible - they make testing harder, apart from anything else. They can occasionally be useful though.

Jon Skeet
Awesome explanation....Can you tell us one instance (real time) where you would find singleton pattern useful? +1
Raja
@Raja: I can't think of any genuine situations at the minute, although that doesn't mean I haven't used any.
Jon Skeet
@Raja this is something I'm going to use alot in .NET 4.0 in my classes that do any reflection `private static readonly ConcurrentDictionary _reflectionCache = new ConcurrentDictionary();`
Chris Marisic
I'm a relatively new programmer. I find myself using Singleton classes for accessing a database. Then from anywhere in my program I can call MyDB.AddRecord(...) where AddRecord is a static method that calls itself on the static instance. Especially for configuration databases it's nice to be able to call the database from wherever instead of passing an object around. This is just my newbie experience. What's your opinion on this approach? Am I setting myself up for a world of hurt down the road by doing this? Just wondering your $0.02USD
bufferz
@bufferz: That tends to make it harder to test things, IMO - you're wiring up everything to that one class, rather than presenting each object with its dependencies.
Jon Skeet
+4  A: 

Here you can find pros and cons of different Singleton implementations in c#

Hun1Ahpu
A: 

So, as far as I am concerned, this is the most concise and simple implementation of the Singleton pattern in C#.

http://blueonionsoftware.com/blog.aspx?p=c6e72c38-2839-4696-990a-3fbf9b2b0ba4

I would, however, suggest that singletons are really ugly patterns... I consider them to be an anti-pattern.

http://blogs.msdn.com/scottdensmore/archive/2004/05/25/140827.aspx

For me, I prefer to have something like a Repository, implementing IRepository. Your class can declare the dependency to IRepository in the constructor and it can be passed in using Dependency Injection or one of these methods:

http://houseofbilz.com/archive/2009/05/02.aspx

Brian Genisio
A: 

Here's a great link that explains different implementations of the singleton pattern: http://www.yoda.arachsys.com/csharp/singleton.html

derek
+1  A: 

There are several Patterns which might be appropriate for you, a singleton is one of the worse.

Registry

struct Data {
  public String ProgramName;
  public String Parameters;
}

class FooRegistry {
  private static Dictionary<String, Data> registry = new Dictionary<String, Data>();
  public static void Register(String key, Data data) {
     FooRegistry.registry[key] = data;
  }
  public static void Get(String key) {
     // Omitted: Check if key exists
     return FooRegistry.registry[key];
  }
}

Advantages

  • Easy to switch to a Mock Object for automated testing
  • You can still store multiple instances but if necessary you have only one instance.

Disadvantages

  • Slightly slower than a Singleton or a global Variable

Static Class

class GlobalStuff {
  public static String ProgramName {get;set;}
  public static String Parameters {get;set;}
  private GlobalStuff() {}
}

Advantages

  • Simple
  • Fast

Disadvantages

  • Hard to switch dynamically to i.e. a Mock Object
  • Hard to switch to another object type if requirements change

Simple Singleton

class DataSingleton {
  private static DataSingleton instance = null;
  private DataSingleton() {]
  public static DataSingleton Instance {
     get {
         if (DataSingleton.instance == null) DataSingleton.instance = new DataSingleton();
         return DataSingleton;
     }
  }
}

Advantages

  • None really

Disadvantages

  • Hard to create a threadsafe singleton, the above Version will fail if multiple threads access the instance.
  • Hard to switch for a mock object

Personally I like the Registry Pattern but YMMV.

You should take a look at Dependency Injection as it's usually considered the best practice but it's too big a topic to explain here.

http://en.wikipedia.org/wiki/Dependency_Injection

dbemerlin
I think your singleton pattern is wrong, that if check inside of the getter isn't thread safe. You want to implement a singleton the as described above by @Jon Skeet. Theoretically 2 threads could enter that getter at the same time both see instance == null and then both execute the 2nd line causing the singleton to mutate by the last out thread.
Chris Marisic
@Chris: I mentioned that this implementation is not threadsafe in the "Disadvantages" section. The Code is there to explain the concept, not to give a fully working example.
dbemerlin