2011-02-25 15 views
8

El patrón de diseño del adaptador se utiliza para convertir la interfaz de una clase (destino) en otra interfaz (Adaptee) que los clientes esperan. El adaptador permite que las clases incompatibles funcionen juntas que no podrían hacerlo de otra forma debido a sus interfaces incompatibles.Implementación del patrón de adaptador

El patrón de adaptador se puede implementar de dos maneras, por Herencia (versión de clase del patrón de adaptador) y por composición (versión de objeto del patrón de adaptador).

Mi pregunta es acerca de la versión de la clase del patrón de adaptador que se implementa con Herencia.

Aquí es un ejemplo de editor de dibujo:

Figure 1:

interface Shape 
{ 
     Rectangle BoundingBox(); 

     Manipulator CreateManipulator(); 
} 

class TextView 
{ 
     public TextView() { } 

     public Point GetOrigin() { } 

     public int GetWidth() { } 

     public int GetHeight() { } 
} 
interface Shape 
{ 
     Rectangle BoundingBox(); 

     Manipulator CreateManipulator(); 
} 

class TextView 
{ 
     public TextView() { } 

     public Point GetOrigin() { } 

     public int GetWidth() { } 

     public int GetHeight() { } 
} 

Nos gustaría volver a utilizar la clase TextView para implementar TextShape, pero las interfaces son diferentes, y por lo tanto, TextView y dar forma a objetos no se pueden usado indistintamente

¿Se debe cambiar la clase TextView para que se ajuste a la interfaz de forma? Talvez no.

TextShape puede adaptar la interfaz de Vista de Texto a la interfaz de la forma, en una de las dos maneras:

  1. Heredando la interfaz de la forma y la implementación de Vista de Texto (versión de la clase de golpeteo adaptador)
  2. Al componer una instancia de Vista de Texto dentro del objeto TextShape e implementando la interfaz de TextShape utilizando la instancia de TextView (versión de objeto del patrón Adapter).

adaptador Clase

Figure 2:

interface Shape 
{ 
    Rectangle BoundingBox(); 

    Manipulator CreateManipulator(); 
} 

class TextView 
{ 
    public TextView() { } 

    public Point GetOrigin() { } 

    public int GetWidth() { } 

    public int GetHeight() { } 
} 

class TextShape : TextView, Shape 
{ 
    public Rectangle BoundingBox() 
    { 
     Rectangle rectangle; 
     int x, y; 
     Point p = GetOrigin(); 
     x = GetWidth(); 
     y = GetHeight(); 

     //... 

     return rectangle; 
    } 

    #region Shape Members 

    public Rectangle Shape.BoundingBox() 
    { 
     return new TextBoundingBox(); 
    } 

    public Manipulator Shape.CreateManipulator() 
    { 
     return new TextManipulator(); 
    } 

    #endregion 
} 

Ahora la pregunta :-). ¿TextShape hereda de Shape y particularmente de TextView una relación "es una" válida? Y si no, ¿no viola Liskov's Substitution Principle?

+0

Creo que no viola LSP estrictamente, pero ¿por qué no usar la forma de componer? Está más desacoplado. – MatejB

Respuesta

4

No viola el Principio de sustitución de Liskov a menos que tenga algo en la subclase que lo haga comportarse de una manera que no tiene sentido para la superclase (violando el contrato de la superclase). Este es un código incompleto, por supuesto, pero no veo ningún signo de eso.

Podría violar el Single Responsibility Principle, pero no estoy seguro de que sea una gran preocupación en la implementación de un adaptador.

Por lo general, prefiero la forma de delegado.

Cuestiones relacionadas