Null Object Refactoring
page 2 of 5
by Brian Mains
Feedback
Average Rating: This article has not yet been rated.
Views (Total / Last 10 Days): 26503/ 108

Review Status Example

Take, for example, the following class.

Listing 1

public class ReviewStatus
{
  private string _code = string.Empty;
  private string _name = string.Empty;
 
  #region " Properties "
 
  public string Code
  {
    get
    {
      return _code;
    }
    set
    {
      _name = value;
    }
  }
 
  public string Name
  {
    get
    {
      return _name;
    }
    set
    {
      _name = value;
    }
  }
 
  #endregion
 
  #region " Constructors "
 
  protected ReviewStatus(string code, string name)
  {
    _code = code;
    _name = name;
  }
 
  #endregion
  public static ReviewStatus Accepted()
  {
    return new ReviewStatus("A", "Accepted");
  }
 
  public static ReviewStatus Cancelled()
  {
    return new ReviewStatus("C", "Cancelled");
  }
 
  public static ReviewStatus Processed()
  {
    return new ReviewStatus("P", "Processed");
  }
 
  public override bool Equals(object obj)
  {
    if (obj == null || !(obj is ReviewStatus))
      return false;
 
    ReviewStatus status = (ReviewStatus)obj;
    return this.Code.Equals(status.Code);
  }
}

This class represents the status of a review in a business system.  It can be Accepted, Cancelled, or Processed, and has two properties that contain the codified and named values.  The review status, though, could have no status to report, especially if a new business object was created and not in the review phase.  To handle this through a Null object we can use the following object.

Listing 2

public class NullReviewStatus: ReviewStatus
{
  #region " Constructors "
  private NullReviewStatus(): base(string.Empty, string.Empty){}
  #endregion
 
  public static ReviewStatus Empty()
  {
    return new NullReviewStatus();
  }
}

Because the constructor on ReviewStatus is declared protected, the NullReviewStatus class can inherit from ReviewStatus to expose a new static method:  Empty().  Empty returns the equivalent of an empty status, meaning no status is assigned by assigning string.Empty values to the code and name parameters.  To note, string.Empty is returned so it does not cause null reference checks when using the properties, like using the Code.Equals() method in the ReviewStatus code sample.

To make null checking easier, Fowler recommends adding an IsNull method, which the ReviewStatus class returns a static value of false.  NullReviewStatus overrides the IsNull method and returns a value of true, noting that the object is null.  This makes it easier to process whether or not the object is actually null.

Listing 3

//ReviewStatus Implementation
public virtual bool IsNull()
{
      return false;
}
//NullReviewStatus Implementation
public override bool IsNull()
{
      return true;
}

An object that uses the ReviewStatus object can default the private variable of a business class to Empty.

Listing 4

private ReviewStatus _review = NullReviewStatus.Empty();

This makes the review status value equal to the nullable object and prevents any null exceptions from using a null reference variable.  Although there are varying preferences in regards to this, I prefer this approach in my business applications for certain object types.


View Entire Article

User Comments

Title: good write-up   
Name: HoyaSaxa93
Date: 2007-05-15 3:26:44 PM
Comment:
good examples of factoring / backing into null objects






Community Advice: ASP | SQL | XML | Regular Expressions | Windows


©Copyright 1998-2024 ASPAlliance.com  |  Page Processed at 2024-10-08 8:54:06 AM  AspAlliance Recent Articles RSS Feed
About ASPAlliance | Newsgroups | Advertise | Authors | Email Lists | Feedback | Link To Us | Privacy | Search