BlackWaspTM

This web site uses cookies. By using the site you accept the cookie policy.This message is for compliance with the UK ICO law.

Design Patterns
.NET 1.1+

Null Object Design Pattern

The null object pattern is a design pattern that simplifies the use of dependencies that can be undefined. This is achieved by using instances of a concrete class that implements a known interface, instead of null references.

Example Null Object

In this section we'll create an implementation of the strategy pattern where one of the strategy classes is a null object. The example shows a sample class named, "StatusMonitor", which performs some action and then reports a status. Three strategy classes are available depending upon the manner in which the status should be reported. They allow reporting by email, sending status messages to a web service or no reporting at all. When no reporting is required, an instance of the null object class, "NullStatusReporter" is provided as the dependency.

Each of the three strategy classes includes a single method that is called to report a message. The EmailStatusReporter and WebServiceStatusReporter classes attempt to report the status, returning true on success and false on failure. The null object version performs no reporting and always returns true, as it cannot fail.

NB: The implementations for the functional strategies are represented by console messages for clarity.

public class StatusMonitor
{
    StatusReporterBase _reporter;

    public StatusMonitor(StatusReporterBase reporter)
    {
        _reporter = reporter;
    }

    public void CheckStatus()
    {
        // Do something to check status
        if (!_reporter.Report("Everything's OK"))
        {
            Console.WriteLine("Failed to report status.");
        }
    }
}


public abstract class StatusReporterBase
{
    public abstract bool Report(string message);
}


public class EmailStatusReporter : StatusReporterBase
{
    public override bool Report(string message)
    {
        try
        {
            Console.WriteLine("Emailed '{0}'.", message);
            return true;
        }
        catch
        {
            return true;
            throw;
        }
    }
}


public class WebServiceStatusReporter : StatusReporterBase
{
    public override bool Report(string message)
    {
        try
        {
            Console.WriteLine("Sent '{0}' to web service.", message);
            return true;
        }
        catch
        {
            return true;
            throw;
        }
    }
}


public class NullStatusReporter : StatusReporterBase
{
    private static NullStatusReporter _instance;
    private static object _lock = new object();

    private NullStatusReporter() { }

    public static NullStatusReporter GetReporter()
    {
        lock (_lock)
        {
            if (_instance == null) _instance = new NullStatusReporter();
        }

        return _instance;
    }

    public override bool Report(string message)
    {
        return true;
    }
}

Testing the Null Object

We can now try out the null object and the other strategies by creating a StatusMonitor object various injected dependencies. The following code provides a null object to the constructor so running CheckStatus outputs no messages. Try supplying the other dependencies to see the results.

StatusReporterBase reporter = NullStatusReporter.GetReporter();
StatusMonitor monitor = new StatusMonitor(reporter);
monitor.CheckStatus();
8 September 2012