Principles in Practice

These universal design principles provide good guidance, but they don’t help with specific languages or platforms. That’s why you need design principles for specific languages, such as Martin’s list of the principles of object-oriented class design.[66] Unfortunately, when you take universal design principles and turn them into specific design advice, you lose something important: context. Every design decision occurs in the context of the whole design—the problem domain, other design decisions, the time schedule, other team members’ capabilities, etc.

Context makes every piece of specific design advice suspect. Yes, you should listen to it—there’s a lot of wisdom out there—but exercise healthy skepticism. Ask yourself, “When is this not true?” and “What is the author assuming?”

Consider the simple and popular “instance variables must be private” design rule. As one of the most widely repeated design rules, it often gets applied without real thought. That’s a shame because without context, the rule is meaningless and easily misused.

It’s true that instance variables should often be private, but if you want to understand the rule and when to break it, ask why. Why make instance variables private? One reason is that private variables enforce encapsulation. But why should anyone care about encapsulation?

The real reason private variables (and encapsulation) are good is that they help enforce decoupling. Decoupled code is good, right? Not always. Appropriately decoupled code is good, but it’s OK for closely related concepts to be tightly coupled.

However, closely related concepts should also be cohesive. They should be close together in the code. In object-oriented programming languages, closely related concepts often belong in the same class.

This is where the “instance variables must be private” rule comes from. When you have an urge to make an instance variable public, it’s a sign that you have both a cohesion problem and a coupling problem. You have a cohesion problem because closely related concepts aren’t in the same class. You have a coupling problem because concepts that the code structure says are unrelated must change together.

The real problem is that programmers follow the letter of the rule without stopping to consider the context. Rather than taking the time to think about coupling and cohesion, many programmers just slap a public accessor and mutator (getter and setter) on a private variable.

Now what good does that do?

  public class MySillyClass {
      private string _myFakeEncapsulatedVariable;

      public string getMyFakeEncapsulatedVariable() {
          return _myFakeEncapsulatedVariable;
      }

      public void setMyFakeEncapsulatedVariable(string var) {
          _myFakeEncapsulatedVariable = var;
      }
  }

From a coupling standpoint, there’s very little difference between this code and code that uses a public variable. The code follows the letter of the rule, but ignores its spirit: don’t let other classes have access to your implementation details! From a design perspective, a public variable is equivalent to this code, and it would certainly make a poor design decision more obvious.



[66] The Single Responsibility Principle, Open-Closed Principle, Liskov Substitution Principle, Dependency-Inversion Principle, and Interface Segregation Principle.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset