Adapter Design Pattern

Download as doc, pdf, or txt
Download as doc, pdf, or txt
You are on page 1of 8

Adapter Design Pattern

Nguyễn Đình Trung – 20215249


I. Name – Alias:
In software engineering, the adapter pattern is a software design pattern (also known as
wrapper, an alternative naming shared with the decorator pattern) that allows the
interface of an existing class to be used as another interface. It is often used to make
existing classes work with others without modifying their source code.

II. Classification:
The Adapter is classified as a structural design pattern because it deals with object
composition and relationships. It helps in forming large object structures and ensures
that these structures can work seamlessly despite having incompatible interfaces.

III. Intent:
The intent of the Adapter design pattern is to enable two incompatible interfaces to work
together. This is done by creating an adapter that acts as a translator between the
interfaces, allowing the client to interact with the adaptee through the adapter without
needing to alter the existing code. The Adapter pattern essentially converts the interface
of a class into another interface that a client expects, facilitating compatibility between
otherwise mismatched components.

IV. Motivation:
4.1 Interface Incompatibility:

Problem: You have two classes with incompatible interfaces, and you need them to work
together.

Example: Your application expects an interface for logging, but the third-party logging
library you want to use has a different interface.

4.2 Legacy System Integration:

Problem: You have legacy systems or components with interfaces that do not match the
interfaces expected by your new application.

Example: An old payment processing system has an interface that is not compatible with
your new e-commerce platform.

4.3 Simplifying Complex Interfaces:

Problem: The interface of an existing class is too complex or cumbersome for client use.

Example: A data processing library has a complex interface, making it difficult for the
client code to use it directly.

4.4 Reuse Without Modification:


Problem: You want to reuse existing classes that have incompatible interfaces without
modifying their source code.

Example: Reusing a set of utility classes from a previous project in a new project where
the interfaces do not match.

4.5 Decoupling Code:

Problem: You want to decouple your code from specific implementations to allow for
easier maintenance and flexibility.

Example: Decoupling your network request handling so you can easily switch between
different network libraries without changing the client code.

V. Solution: Solution using DP

5.1: Class Diagram

5.2: Interactive Diagram:


5.3: Explanation of Code and Diagram
Class Diagram Breakdown

MediaPlayer: Target interface expected by the client.

AdvancedMediaPlayer: Interface for the advanced media player.

VlcPlayer and Mp4Player: Implementations of the AdvancedMediaPlayer interface.

MediaAdapter: Adapter class that implements MediaPlayer and uses an instance of


AdvancedMediaPlayer to play the requested media.

AudioPlayer: Client class that uses MediaPlayer to play different types of media files.

Interactive Diagram Breakdown

Client: Initiates the interaction by calling the play method on AudioPlayer.

AudioPlayer: Checks the media type and uses MediaAdapter if necessary.

MediaAdapter: Translates the request to the appropriate method of


AdvancedMediaPlayer.

AdvancedMediaPlayer: Plays the media using the specific implementation (either


VlcPlayer or Mp4Player).

5.4: Illustrated source code

5.4.1: Target Interface:


public interface MediaPlayer {

void play(String audioType, String fileName);

5.4.2: Adaptee Interface and Classes:


public interface AdvancedMediaPlayer {

void playVlc(String fileName);

void playMp4(String fileName);

public class VlcPlayer implements AdvancedMediaPlayer {

@Override

public void playVlc(String fileName) {

System.out.println("Playing vlc file. Name: " + fileName);

}
@Override

public void playMp4(String fileName) {

public class Mp4Player implements AdvancedMediaPlayer {

@Override

public void playVlc(String fileName) {

@Override

public void playMp4(String fileName) {

System.out.println("Playing mp4 file. Name: " + fileName);

5.4.3: Adapter Class


public class MediaAdapter implements MediaPlayer {

AdvancedMediaPlayer advancedMusicPlayer;

public MediaAdapter(String audioType) {

if(audioType.equalsIgnoreCase("vlc")) {

advancedMusicPlayer = new VlcPlayer();

} else if (audioType.equalsIgnoreCase("mp4")) {

advancedMusicPlayer = new Mp4Player();

@Override

public void play(String audioType, String fileName) {


if(audioType.equalsIgnoreCase("vlc")) {

advancedMusicPlayer.playVlc(fileName);

} else if(audioType.equalsIgnoreCase("mp4")) {

advancedMusicPlayer.playMp4(fileName);

5.4.4: Client Class


public class AudioPlayer implements MediaPlayer {

MediaAdapter mediaAdapter;

@Override

public void play(String audioType, String fileName) {

if(audioType.equalsIgnoreCase("mp3")) {

System.out.println("Playing mp3 file. Name: " + fileName);

} else if(audioType.equalsIgnoreCase("vlc") ||
audioType.equalsIgnoreCase("mp4")) {

mediaAdapter = new MediaAdapter(audioType);

mediaAdapter.play(audioType, fileName);

} else {

System.out.println("Invalid media. " + audioType + " format not supported");

public class AdapterPatternDemo {

public static void main(String[] args) {

AudioPlayer audioPlayer = new AudioPlayer();

audioPlayer.play("mp3", "beyond_the_horizon.mp3");
audioPlayer.play("mp4", "alone.mp4");

audioPlayer.play("vlc", "far_far_away.vlc");

audioPlayer.play("avi", "mind_me.avi");

VI. Pros and Cons


VI.3 Advantage:

- Promotes Reusability:

Explanation: The Adapter pattern allows existing classes to be reused, even if their
interfaces are incompatible with the current application.

Benefit: This can save development time and resources, as existing code can be
leveraged without modification.

- Improves Flexibility:

Explanation: By decoupling the client from the implementation details of the


Adaptee, the Adapter pattern allows for more flexible code.

Benefit: This makes it easier to swap out implementations without affecting the client
code.

- Enhances Maintainability:

Explanation: The Adapter encapsulates the complexity of the Adaptee, providing a


simplified interface to the client.

Benefit: This can make the codebase easier to understand and maintain, as the
client interacts with a more straightforward interface.

- Facilitates Integration of Legacy Systems:

Explanation: The Adapter pattern is particularly useful for integrating legacy systems
with new systems that have different interfaces.

Benefit: This allows businesses to modernize their systems incrementally without a


complete overhaul.
- Supports Single Responsibility Principle:

Explanation: The Adapter pattern helps to keep the client code focused on its
primary responsibility while the adapter handles the interface translation.

Benefit: This separation of concerns can lead to cleaner and more manageable
code.

VI.3 Disadvantage:

- Increased Complexity:

Explanation: The introduction of an adapter adds an additional layer of abstraction,


which can increase the overall complexity of the system.

Drawback: This additional complexity might make the system harder to understand
and debug, especially for new developers.

- Performance Overhead:

Explanation: The adapter introduces an additional layer of method calls between the
client and the adaptee.

Drawback: This can result in a slight performance overhead, which might be


significant in performance-critical applications.

- Maintenance of Extra Code:

Explanation: The Adapter pattern requires additional code to be written and


maintained.

Drawback: This increases the codebase and can add to the maintenance burden,
especially if multiple adapters are needed.

- May Lead to Overuse:

Explanation: The Adapter pattern can be overused as a quick fix to integrate


incompatible interfaces without considering other design improvements.

Drawback: Overuse of adapters can lead to a fragmented and inconsistent


codebase, where too many adapters complicate the overall architecture.

- Limited to Existing Interfaces:

Explanation: The Adapter pattern can only adapt existing interfaces; it cannot
change the behavior of the adaptee.
Drawback: If the adaptee's functionality needs to be modified rather than just its
interface, the Adapter pattern may not be sufficient.

VII. Applicability
- Software Libraries and Frameworks Integration

- User Interface Components

- Database Connectivity

- Payment Processing Systems

- File Systems

- Device Communication

The Adapter design pattern is widely applicable in real-life scenarios where systems
need to integrate or adapt different interfaces. These examples illustrate how the pattern
can resolve compatibility issues across various domains, such as software libraries, UI
components, database connectivity, payment processing, file systems, and device
communication. By using the Adapter pattern, developers can achieve seamless
integration and reuse existing components without modifying their underlying code.

You might also like

pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy