Design Patterns #6: Adapter

Continuing with design patterns. Time for Adapter. This pattern is a structural pattern whose purpose is to convert interface (in a meaning of public members of the class, not necessarily interface as a programming language feature) so the class is usable with client’s code. The Head First book defines this pattern as:

The Adapter Pattern converts the interface of a class into another interface the client expects. Adapter lets classes work that couldn’t otherwise because of incompatible interfaces.
(Freeman, Eric, et al. Head First Design Patterns. O’Reilly Media, Inc. 2004)

Generally, it may be said that the adapter pattern wraps an object that cannot be used by a client and exposes an interface that allow the client to use that object. Let’s take a look at the diagram:

So, we have a client that wants to use an object that implements IExpected interface, however we already have a class that does what we need but doesn’t have a compatible interface (unsupported class). So, to solve the problem we need an adapter. The adapter will have all public members that the client expects – will implement the IExpected interface and at the same time will privately wrap an instance of unsupported class (passed in a constructor, for instance). Once the client calls the adapter, the adapter will in turn call the wrapped unsupported class and return results to the client (and if required convert them to what the client expects). And that’s it, simple as that.

Let’s take a look at code example now. We have a class that calculates area and perimeter of a rectangle. (These calculations are very simple but to give the example a little bit more depth think of them as of very sophisticated and complicated). That class operates on double type. Our client, however wants to calculate area and perimeter of squares only and operates on integers. We could i) write a new class to handle that but we don’t want to do that because we already have a class that is capable to perform such calculations (square is a rectangle after all, right?); ii) modify our client to work with the existing class, but again we don’t want to break anything elsewhere (OCP right?). That’s why the right solution here is the adapter.
Let’s compare what we have and what we need:

So, the differences are: i) types (already mentioned int vs. double), ii) method names, iii) number or arguments required for counterparting methods.
Now the adapter. First of all it needs to wrap the already existing class and set its instance by passing it through constructor; then we need to implement methods required by IExpected interface in a way that they call the wrapped object and return values converted to integers.

Let’s write a quick test:

Everything works perfectly.

Object adapter vs. Class adapter
The explanation and code example is an object adapter. This means that the adapter works with a concrete instance of adapted object. Advantage of this solution is that this type of adapter will work also with objects of classes which are derived from adapted superclass.
There is also another adapter-type pattern called class adapter. In this type you don’t need an instance of adapted class, instead the adapter class inherits from both: expected class (or interface) and adapted class. Remember that inheriting from more than one superclass is not possible, what could be done is to create new class that inherits from a class that needs to be adapted and implements expected interface. This approach may also be useful but keep in mind that it looses the advantage of composition over inheritance.

To sum things up: adapters are extremely useful everywhere there is a need to use something that can do what we need but doesn’t have compatible interface.
Plan for next week: Facade

Don’t forget to check the links below!

Christopher Okhravi about Adapter Pattern: [YouTube]
Source code: [TXT file]