Design Patterns in Ruby: Strategy

A clear example of the Strategy pattern

A clear example

The intent

According to the GoF, the intent of the Strategy pattern is to:

“Define a family of algorithms, encapsulate each one, and make them interchangeable. Strategy lets the algorithm vary independently from clients that use it.”

The example

In the example below, an instance of the Car class accepts an engine strategy. There are two engine strategies defined, StraightSixEngine and V8Engine. Each encapsulates a variant of an engine algorithm. Each shares a common interface (meaning that they share the same public methods).

The Strategy pattern in action

Some tidbits

The strategies share an interface

When using the Strategy pattern you should be sure to couple clients to the interface shared by each of the strategies, and not to any concrete strategy. In Ruby, which lacks formal interfaces, this merely means that each strategy in the family of algorithms share the same public API (the same public methods).

Getting rid of if statements

The Strategy pattern is often used to eliminate conditional statements within a class. Sometimes, when you have different algorithms for a desired behavior and the algorithm is chosen conditionally, it makes sense to encapsulate those algorithms into classes (strategies) and eliminate the conditionals altogether.

Composition over Inheritance

Because the Strategy pattern uses composition instead of inheritance, it is often considered superior to solutions favoring inheritance.

Going deeper

There are many contexts in which the use of the Strategy pattern is prudent. To learn more, check out the seminal work on Design Patterns: The GOF Design Pattern book.