0
0
CsharpHow-ToBeginner · 3 min read

How to Create Singleton in C#: Simple Guide

To create a singleton in C#, define a class with a private constructor and a static readonly instance property that returns the single object. Use lazy initialization with Lazy<T> for thread safety and to ensure only one instance is created.
📐

Syntax

The singleton pattern in C# uses a private constructor to prevent external instantiation, a private static readonly field to hold the single instance, and a public static property to provide global access to that instance.

  • private constructor: stops creating new objects from outside.
  • static readonly instance: holds the single object.
  • public static property: returns the single instance.
  • Lazy<T>: ensures thread-safe, lazy creation.
csharp
public sealed class Singleton
{
    private static readonly Lazy<Singleton> instance = new Lazy<Singleton>(() => new Singleton());

    private Singleton()
    {
        // Private constructor prevents external instantiation
    }

    public static Singleton Instance
    {
        get
        {
            return instance.Value;
        }
    }
}
💻

Example

This example shows how to use the singleton class. It prints the same instance's hash code twice, proving only one object exists.

csharp
using System;

public sealed class Singleton
{
    private static readonly Lazy<Singleton> instance = new Lazy<Singleton>(() => new Singleton());

    private Singleton()
    {
        // Private constructor
    }

    public static Singleton Instance => instance.Value;

    public void ShowMessage()
    {
        Console.WriteLine("Singleton instance hash code: " + this.GetHashCode());
    }
}

class Program
{
    static void Main()
    {
        Singleton s1 = Singleton.Instance;
        Singleton s2 = Singleton.Instance;

        s1.ShowMessage();
        s2.ShowMessage();

        Console.WriteLine("Are both instances equal? " + (s1 == s2));
    }
}
Output
Singleton instance hash code: 46104728 Singleton instance hash code: 46104728 Are both instances equal? True
⚠️

Common Pitfalls

Common mistakes when creating singletons in C# include:

  • Not making the constructor private, allowing multiple instances.
  • Not handling thread safety, causing multiple instances in multithreaded apps.
  • Using a public static field instead of a property, which is less flexible.
  • Creating the instance eagerly without need, wasting resources.

Always use Lazy<T> or locks to ensure thread safety.

csharp
/* Wrong way: public constructor allows multiple instances */
public class WrongSingleton
{
    public static WrongSingleton Instance = new WrongSingleton();

    public WrongSingleton() { }
}

/* Right way: private constructor and Lazy<T> for thread safety */
public sealed class RightSingleton
{
    private static readonly Lazy<RightSingleton> instance = new Lazy<RightSingleton>(() => new RightSingleton());

    private RightSingleton() { }

    public static RightSingleton Instance => instance.Value;
}
📊

Quick Reference

Singleton Pattern Cheat Sheet:

  • Class: sealed to prevent inheritance.
  • Constructor: private to block external creation.
  • Instance: static readonly Lazy<T> for lazy, thread-safe creation.
  • Access: public static property returns the instance.

Key Takeaways

Use a private constructor to prevent creating multiple instances.
Use static readonly Lazy for thread-safe, lazy initialization.
Access the singleton instance via a public static property.
Avoid public constructors and non-thread-safe code to prevent bugs.
Singleton ensures only one instance exists during app lifetime.