Mahdi
Mahdi

Reputation: 2283

NullObject Pattern: How to handle fields?

Suppose we have Book class which contains year_published public field. If I want to implement NullObject design pattern, I will need to define NullBook class which behaves same as Book but does not do anything.

Question is, what should be the behavior of NullBook when it's fields are being assigned?

Book book = find_book(id_value);  //this method returns a NullBook instance because it cannot find the book
book.year_published = 2016;  //What should we do here?!

Upvotes: 1

Views: 75

Answers (2)

GhostCat
GhostCat

Reputation: 140457

Thing is: patterns are about balancing. Yes, it is in general good practice to not return null, but to having else to return; but well: what is returned should still make sense!

And to a certain degree, I don't see how having a "NullBook" really helps with the design of your application. Especially as you allow access to various internal fields. You exactly asked the correct question: what should be the published year, or author, or ... of such a "NullBook"?! What happens for example when some piece of code does a "lookup" on books from different "sources"; and then tries to sort those books on the published year. You sure don't want your NullBook to ever be part of such data.

Thus I fail to see the value in having this class, to the contrary: I see it creating a potential for "interesting" bugs; thus my answer is: step back and re-consider if you really need that class.

There are alternatives to null-replacing objects: maybe your language allows for Optionals; or, you rework those methods that could return null ... to return a collection/array of books; and in doubt: that list/array is simply empty.

Long story short: allowing other classes direct access to private fields is a much more of an import design smell; so you shouldn't be too focused on NullObjects, while giving up on such essential things as Information Hiding so easily on the other hand.

Upvotes: 1

olibiaz
olibiaz

Reputation: 2595

The first thing you should do is to make your properties private.

class NullBook {
    private year_published;
    // OR solution2 private year_published = null;

    public setYearPublished(year_published) {
        this.year_published = null;
        // OR solution2 do nothing!
    }
}

You can also define the field private in the parent class, so the children will have to implement the setter to acces the field

class Book {
  private year_published;

  public setYearPublished(year_published) {
     this.year_published = year_published;
  }
}

class NullBook extends Book {
    public setYearPublished(year_published) {
        parent::setYearPublished(null);
    }
}

Why use getters and setters? https://stackoverflow.com/a/1568230/2377164

Upvotes: 1

Related Questions