study of Design Patterns (1994)
Decouple an abstraction from its implementation so that the two can vary independently.
Handle/Body
Inheritance is usually the way when an abstraction can have several implementations. Sometimes it is not flexible enough.
Say, Window
abstract class has many product subclasses IconWindow
, ButtonWindow
etc. Then, to support platforms, you have explosion of subclasses. (# of product kind) x (# of platforms to support)
. Better managed in two hiearchies Window
for type, WindowImpl
for platform.
Also, client code becomes dependent on the platform. for example , to use window on macOS, you would need to instantiate MacIconWindow
, MacButtonWindow
etc., not just IconWindow
or ButtonWindow
. This makes porting really difficult. Clients should be able to create a window w/o commiting to a concrete information. i.e. instantiate windows w/o mentioning specific platforms.
diagram from book
This relationship between Window
andWindowImpl
abstract classes is Bridge.
Use when
Also eliminates compile-time dependencies. Changing an implementation class doesn’t require recompiling the Abstraction class and its clients. Essential when binary compatibility for difference versions of a class library.
Encourage layering that can lead to a better-structured system.
size
, then use linked list. if larger size
, hash table etc.Another approach is to choose a default, then change it later accordingly. ex. If collection grows too big, change to hash table.
Also possible to delegate the decision to another oject altogeter. In the Window/WindowImp example, we can introduce a factory object (see Abstract Factory (87)) whose sole duty is to encapsulate platform-specifics. The factory knows what kind of WindowImp object to create for the platform in use; a Window simply asks it for a WindowImp, and it returns the right kind. A benefit of this approach is that Abstraction is not coupled directly to any of the Implementor classes.
Handle& Handle::operator= (const Handle& other) {
other._body->Ref();
_body->Unref();
if(_body->RefCount() == 0_ {
delete _body;
}
_body = other._body;
return *this;
In book, C++. I rewrite it in python3 skipping details.
only skim thru. What is an ET++? libg++? NXImage?
Abstract Factory to create and configure a particular Bridge.
The Adapter pattern is geared toward making unrelated classes work together. It is usually applied to systems after they’re designed. Bridge, on the other hand, is used up-front in a design to let abstractions and implementations vary independently.