Вы находитесь на странице: 1из 13

Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 1

Patrones de comportamiento
Estado
INTENCION
Permite que un objeto cambie su comportamiento dependiendo de su estado.
El objeto aparentará que cambia de clase.
CONOCIDO COMO
State
MOTIVO
Cuando un objeto puede estar en diferentes estados y el resultado de una
petición a este objeto depende del estado en el que se encuentre, debemos
utilizar este patrón. La idea es introducir una clase abstracta que represente
los distintos estados, para luego hacer subclases. Desde la clase del objeto
se tendrá una referencia a la clase abstracta, a la que se reenviarán las
peticiones recibidas. En el Design Patterns, el ejemplo que se sigue es el de
una conexión TCP.

Incorpora a los patrones el concepto de "Maquina Abstracta" o autómata,


utilizado desde los orígenes de la Informática y estudiado mucho antes.

Ofrece un modelo basado en la programación orientada a objetos frente a las


formas clásicas de programación de autómatas finitos.

APLICACIONES
Cuando el comportamiento de un objeto depende de su estado y debe
cambiar este comportamiento en tiempo de ejecución dependiendo de su
estado.

Para aquellos sistemas que representemos como un autómata o máquina


abstracta
ESTRUCTURA

PARTICIPANTES
 AppContexto
o Define la interfaz de interés para los clientes
o Mantiene
 AppState
o Define una interfaz para encapsular el comportamiento
asociado con un estado particular del contexto.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 2

 EstadoConcreto*
o Cada subclase implementa un comportamiento asociado con
un estado del contexto.

COLABORACIONES

 Contexto delega las peticiones específicas del estado al objeto


EstadoConcreto actual.
 El contexto podría pasarse a sí mismo como parámetro al objeto
estado que maneja la petición. De esta manera se le permite al estado
acceder al contexto si es necesario.
 Contexto es la interfaz principal para los clientes. Los clientes pueden
configurar el contexto con estados.
 Tanto el contexto como el EstadoConcreto pueden decidir qué estado
sigue a cual y bajo qué circunstancias.
CONSECUENCIAS
 Se localiza el comportamiento específico del estado. Todo el
comportamiento asociado con un estado estará en una misma clase.
 Se pueden añadir fácilmente nuevos estados. Heredando de la
superclase.
 Hace explícitos los cambios de estado.
IMPLEMENTACIÓN
 ¿Quién define las transiciones de estado? Si las transiciones son fijas,
se podrían implementar en el contexto, de todas maneras suele ser más
apropiado y flexible dejar a las subclases de Estado especificar su
sucesor. La desventaja de este método es que cada clase Estado debe
tener conocimiento de al menos otra clase Estado.
 Una alternativa basada en una tabla. La ventaja es su regularidad,
pudiendo modificar los criterios de transición sin modificar el código. Las
desventajas son la menor eficiencia, más difícil de entender, es difícil
añadir acciones que acompañen a las transiciones entre objetos.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 3

 Crear y destruir objetos Estado. Hay que elegir entre crear los objetos
Estado cuando se necesiten y destruirlos después, o crearlos con
anterioridad y no destruirlos.
CODIGO DE EJEMPLO

USOS CONOCIDOS
Protocolos TCP.
Herramientas de dibujo.
StateEdit AccesibleState DirStateFactory StateEditable StateFactory
P. RELACIONADOS
El patrón Flyweight explica cuándo y cómo se pueden compartir objetos
Estado
Los estados son habitualmente Singletons.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 4

Observador
INTENCION
Notifica automáticamente de los cambios de estado de un objeto a todos sus
dependientes.

Permite de forma dinámica implementar dependencias entre objetos, de forma


que los objetos dependientes sean notificados de los cambios que se producen
en los objetos de los que dependen.

CONOCIDO COMO
Observer
MOTIVO
Un efecto común de particionar un sistema en una colección de clases que
cooperan es la necesidad de mantener la consistencia entre objetos
relacionados sin hacer las clases demasiado dependientes entre sí, ya que
esto reduce su reusabilidad.
El ejemplo del Design Patterns es el de modelo y diferentes vistas.
El patrón Observador describe cómo establecer estas relaciones. Tendríamos
un sujeto y varios observadores. Todos los observadores son notificados
cuando el estado del sujeto cambia.
APLICACIONES
 Cuando un sistema requiere que unos elementos sean conscientes de
los cambios producidos en otros.
 Cuando la dependencia entre instancias se produce de forma
dinámica, en tiempo de ejecución y no siempre.
 Cuando la dependencia se produce de un objeto hacia muchos y un
sistema simple de eventos no sirve porque solo permite notificar a una
sola instancia.
 Cuando se quiere que un objeto notifique a otros sin conocer qué tipo
de objetos son.
 En ocasiones se implementan sistemas de eventos mediante este
sistema, por ejemplo en el API de Java, de forma que los objetos que
notifican de eventos implementan el interfaz observable y los que reciben
las notificaciones de eventos implementan el interfaz observer. Esto
permite que muchos objetos reciban eventos de otro objeto en lugar de
los sistemas de eventos básicos que solo permiten notificar a un único
objeto.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 5

ESTRUCTURA

PARTICIPANTES
 Sujeto (Observable)
o Conoce a sus observadores
o Proporciona una interfaz para añadir y separar objetos
observadores
 Observer
o Define un interfaz de actualización para los objetos que deben
ser notificados de los cambios.
 SujetoConcreto
o Almacena el estado de interés para los observadores
o Manda una notificación a sus observadores cuando cambia su
estado
 ObservadorConcreto
o Mantiene una referencia al sujeto concreto
o Almacena el estado que debe ser consistente con el sujeto
o Implementa el interfaz de actualización de Observer para
mantener su estado consistente con el del sujeto
COLABORACIONES
El sujeto concreto notifica a sus observadores cuando ocurre algún cambio que
podría hacer que el estado de los observadores fuese inconsistente con el
suyo.
Tras ser informados de un cambio en el sujeto concreto, el observador podría
pedir información al sujeto.
CONSECUENCIAS
 Acoplamiento abstracto y mínimo entre el sujeto y el observador.
 Soporte para comunicación broadcast
 Actualizaciones inesperadas. Cada observador no es consciente del
resto de los observadores, se establece una comunicación entre ellos que
no es explícita, por lo tanto no se puede saber qué consecuencias puede
tener cualquier cambio en el sujeto. Además el hecho de que el protocolo
de actualización no indique qué es lo que cambia, agrava este hecho.
IMPLEMENTACIÓN
Generalmente el objeto Observable al notificar al objeto Observer le pasa una
referencia de si mismo como parámetro del método notify (o de alguna otra
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 6

forma) de manera que el objeto receptor de la notificación puede acceder a los


atributos del objeto que observa. Hay que tener en cuenta que un mismo
objeto observer puede haberse registrado como observador de varios objetos
observables, de forma que cuando le llega la notificación necesita saber de
quien le viene.

Independientemente de cómo se implemente la solución a esto siempre


llegarás a la conclusión de que las formas más prácticas requieren que la clase
Observer conozca concretamente la clase Observable o se utilicen interfaces
específicos para cada tipo de notificación según la clase origen, lo cual se
presenta frecuentemente como una desventaja o inconveniente, pero... ¿de
qué otra forma se puede acceder a los atributos de una clase si no es
conociéndola o utilizando un interfaz específico?

En ocasiones conviene reducir el número de notificaciones simplemente por


que se van a producir más cambios, en este caso se espera a que se
produzcan todos los cambios y se retrasa la notificación hasta que se han
completado todos. Se puede implementar añadiendo dos métodos a la clase
Observable para indicar el comienzo de cambios y el final de los mismos, de
forma que las notificaciones están desactivadas entre tanto. Esta solución se
complica si son múltiples objetos los que participan en ese conjunto de
cambios, se puede utilizar un patrón Mediator en este caso.

En el Design Patterns vienen hasta 9 puntos a tener en cuenta en la


implementación.

CODIGO DE EJEMPLO

USOS CONOCIDOS
 MVC (Model/View/Controller) en Smalltalk
 Delegación de eventos en Java.
 ImageObserver
 Observer – Observable.
 TileObserver
P. RELACIONADOS
 Mediator. Se puede utilizar para coordinar múltiples cambios de
estado de un mismo Observable provocados por diferentes objetos (con
la finalidad de reducir el número de notificaciones) (Manejador de
cambios)
 Singleton. El manejador de cambios sería un singleton.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 7

Estrategia
INTENCION
Abstracción para seleccionar un algoritmo de entre una familia de varios.
Permite a los algoritmos variar independientemente de los clientes que lo
usen.
CONOCIDO COMO
Strategy
MOTIVO
Encapsula varios algoritmos alternativos en diferentes clases y se ofrece un
interfaz único (mediante una superclase) para acceder a la funcionalidad
ofrecida, la elección del algoritmo se vuelve transparente para el cliente,
pudiendo depender del objeto e incluso variar en tiempo de ejecución.

Ejemplo del Design Patterns, distintos algoritmos para dividir un texto en


líneas. Ejemplo Bruce Eckel, distintos métodos para hallar el mínimo de una
función.

Una operación de "Guardar" un documento puede ser distinta según sea el


destino elegido un directorio local o un servidor ftp remoto.

La funcionalidad de comprobación de integridad de un archivo puede


realizarse mediante CRC u otro algoritmo.

Un sistema puede requerir cifrar un contenido mediante diferentes métodos


de encriptación.
APLICACIONES
 Varias clases relacionadas se diferencian sólo en su comportamiento.
Proporciona un método de configurar una clase con varios
comportamientos.
 Se necesitan diferentes variantes de un algoritmo. Por ejemplo con
diferentes necesidades de tiempo/espacio.
 Un algoritmo usa datos que el cliente no debería conocer.
 Una clase define muchos comportamientos, y estos aparecen en
sentencias de bifurcación múltiple (switch case)
ESTRUCTURA

PARTICIPANTES
 El Cliente delega una operación en la superclase, abstrayéndose de
los detalles de la misma.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 8

 La superclase AlgoritmoAbstracto ofrece un interfaz común y oculta


la elección del algoritmo empleado.
 Las clases AlgoritmoConcreto implementa cada una de las
diferentes alternativas del algoritmo.
COLABORACIONES
 Cliente (contexto) y AlgoritmoAbstracto (estrategia) interactúan para
implementar el algoritmo elegido. El cliente podría pasar los datos que
necesite el algoritmo. También podría pasarse a sí mismo como
parámetro, así sería el algoritmo el que llamaría al cliente cuando lo
necesitase.
 El contexto(cliente) reenvía las peticiones de sus clientes al
AlgoritmoAbstracto. Los clientes habitualmente configuran al contexto
(cliente) con un AlgoritmoConcreto.

CONSECUENCIAS
 Las jerarquías de estrategias permiten definir una familia de
algoritmos o comportamientos para que los reutilicen los contextos.
 Podríamos hacer algo parecido simplemente heredando y
sobrescribiendo, pero esto acopla en exceso el comportamiento dentro
del contexto. Además no se podría variar el comportamiento en tiempo de
ejecución
 El patrón estrategia elimina las sentencias condicionales para
seleccionar el comportamiento deseado.
 Puede proporcionar varias implementaciones para el mismo
comportamiento.
 Los clientes deben conocer las estrategias y sus diferencias.
 Habrá implementaciones que no usen todos los parámetros que
nosotros pasemos al método.
 Se incrementa el número de objetos.
IMPLEMENTACIÓN
 Hay que definir la interfaz entre contexto y estrategia. Bien el contexto
puede pasar los datos por parámetro, lo que reduce el acoplamiento, pero
podría pasar datos innecesarios; o podría pasarse a sí mismo como
parámetro, de manera que la estrategia le pide lo que necesita, con lo
que se aumenta el acoplamiento.
 Se puede hacer la estrategia opcional, proporcionando un
comportamiento por defecto y la posibilidad de usar un objeto estrategia.
si no existe estrategia, se ejecuta el comportamiento por defecto.
CODIGO DE EJEMPLO
En Bruce Eckel ejemplo de encontrar el mínimo de una función.
USOS CONOCIDOS
El paquete java.util.zip en las clases CheckedInputStream y
CheckedOutputStream utiliza la clase Checksum la cual sigue el patrón
Strategy para elegir entre los algoritmos de comprobación de errores en
Streams de bytes ya sea CRC32 o Adler32.
P. RELACIONADOS
Si existen muchas instancias de Cliente es mejor utilizar el patrón Flyweights
en lugar de Strategy.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 9

Template method

INTENCION
Define el esqueleto de un algoritmo en una operación, posponiendo algunos
pasos a las subclases. Permite a las subclases redefinir ciertos pasos de un
algoritmo sin cambiar la estructura del mismo.
CONOCIDO COMO
Template method (método plantilla)
MOTIVO
En el ejemplo de una aplicación framework que trabaja con documentos, el
método abrir documento podría ser un método plantilla que preguntase si se
puede abrir y si es así, que lo añada a la lista de documentos abiertos, lo
abra y lo lea.
Al definir algunos de los pasos de un algoritmo usando métodos abstractos,
el método plantilla fija su orden, pero permite a las subclases variar esas
implementaciones para que se ajusten a sus necesidades.
APLICACIONES
 Para implementar la parte invariante de un algoritmo y permitir a las
subclases que implementen la parte que varía.
 Cuando el comportamiento común entre las subclases debe ser
factorizado y localizado en una clase común para evitar que se duplique
código.
ESTRUCTURA

PARTICIPANTES
 Clase Abstracta define los métodos operación que las subclases
concretas implementarán, e implementa el método plantilla (algoritmo)
con el esqueleto del algoritmo, este método llama a los métodos
abstractos.
 Clase Concreta Debe implementar los métodos operación para llevar
a cabo las operaciones específicos de la subclase.
COLABORACIONES
La ClaseConcreta depende de la ClaseAbstracta para implementar los pasos
invariantes del algoritmo.
CONSECUENCIAS
Los métodos plantilla son una técnica fundamental para la reutilización de
código, sobre todo en las bibliotecas de clases, porque factorizan el
comportamiento común.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 10

Este patrón nos lleva a una estructura de control invertida en la que las
superclases llaman a las subclases y no al revés (el principio de Hollywood).
IMPLEMENTACIÓN
 Las operaciones primitivas se pueden declara protected, para que sólo
se las pueda llamar desde el método plantilla. El método plantilla se
podría declarar final para que no se pueda sobrescribir.
 Hay que minimizar el número de operaciones primitivas.
CODIGO DE EJEMPLO

USOS CONOCIDOS
Los métodos plantilla son tan fundamentales que se pueden encontrar en
casi cualquier clase abstracta
P. RELACIONADOS
El patrón Template Method usa la herencia para variar una parte del
algoritmo. El patrón Strategy usa delegación para variar el algoritmo entero.

Los métodos factoría son llamados a menudo por lo métodos plantilla.


Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 11

Command (sin terminar)


INTENCION
Encapsula una petición como un objeto, esto facilita la parametrización de los
requerimientos (inicialización de los parámetros por el constructor), el encolado
de múltiples peticiones (estructura de datos de objetos comando) y su
reordenación, y permite implementar el hacer/deshacer (do/undo) mediante
métodos.

Por otro lado se facilita la creación de macros agrupando los comandos más
frecuentes.

CONOCIDO COMO
Command, action, transaction.
MOTIVO
El concepto de "comando" puede ser ambiguo y complejo en los sistemas
actuales y al mismo tiempo muy extendido: intépretes de comandos del sistema
operativo, lenguajes de macros de paquetes ofimáticos, gestores de bases de
datos, protocolos de servidores de Internet, etc.

Este patrón presenta una forma sencilla y versátil de implementar un sistema


basado en comandos facilitándose su uso y ampliación.

APLICACIONES
Cuando se requiera:
 Facilitar la parametrización de las acciones a realizar.
 Independizar el momento de petición del de ejecución.
 Implementar CallBacks, especificando que comandos queremos que se
ejecuten en ciertas situaciones de otros comandos. Es decir un
parámetro de un comando puede ser otro comando a ejecutar.
 Soportar el "deshacer".
 Desarrollar sistemas utilizando comandos de alto nivel que se
construyen con operaciones más sencillas (primitivas).

ESTRUCTURA
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 12

PARTICIPANTES
AbstractCommand. Clase que ofrece un interfaz para la ejecución de
comandos. Define los métodos do y undo que se implementarán en cada clase
concreta.

ConcreteCommand. Clase que implementa un comando concreto y sus


métodos do y undo. Su constructor debe inicializar los parámetros del
comando.

Invoker. Clase que instancia los comandos, puede a su vez ejecutarlos


inmediatamente (llamando a do) o dejar que el CommandManager lo haga.

CommandManager. Responsable de gestionar una colección de objetos


comando creadas por el Invoker. llamará a los métodos doIt y unDoIt.
Gestionará su secuenciación y reordenación (en base a prioridades por
ejemplo).

COLABORACIONES

CONSECUENCIAS
 Se independiza la parte de la aplicación que invoca los comandos de la
implementación de los mismos.
 Al tratarse los comandos como objetos, se puede realizar herencia de
los mismos, composiciones de comandos (mediante el patrón
Composite)
 Se facilita la ampliación del conjunto de comandos.

IMPLEMENTACIÓN
Combiene estudiar el conjunto de comandos a implementar y si se observan
comandos demasiado complejos dividirlos en subcomandos más sencillos y
utilizarlos de forma combinada.
Ricardo Sosa Sánchez-Cortés – Diseño Orientado a Objetos 13

Si se implementan las operaciones Undo hay que almacenar el estado de los


objetos que se modifiquen para su posterior restauración al ejecutar Undo
(pensar en el patrón Memento).

Pueden aparecer comandos cuya acción sea imposible Deshacer (como el


borrado de archivos)

Si se dota al manejador de comando de un mecanismo para que sea


consciente de que comandos se pueden deshacer y cuales no, entonces
podemos centralizar el tratamiento de los mismos en el manejador, por ejemplo
puede comportarse advirtiendo al usuario de que tal operación no podrá
deshacerse dandole la opción de cancelarlo.

Si el manejador de comandos ejecuta un comando que no se puede deshacer y


es consciende de ello puede borrar el historial de comandos ya que no se va a
poder volver atrás. Esto supone un ahorro de memoria considerable ya que se
descartan todos los estados guardados de los comandos previos.

Se puede implementar un sistema de direccionamiento hacia los comandos


mediante Factory Method.

CODIGO DE EJEMPLO

USOS CONOCIDOS
Las clases Button y MenuItem de Java facilitan la utilización de este patrón,
declaran los métodos getActionCommand y setActionCommand para dar
nombres a las acciones realizadas por los objetos, facilitandose una
correspondencia entre ambos.
P. RELACIONADOS
 Factory Method Ofrece una forma alternativa de llamar a los comandos
además del uso del command manager.
 Interprete Se puede imnplementar un pequeño Interprete mediante
clases Command.
 Snapshot Puede facilitar el almacenamiento del estado de los objetos
para implementar la acción Deshacer en lugar de utilizar comandos
inversos.
 Template Method Puede servir para implementar la lógica de Deshacer
de forma un tanto automática o a alto nivel.
 Composite Permite realizar agrupaciones de comandos de forma similar
a una macro.
 Prototype Hay quien lo utiliza para implementar la copia del comando al
historico de comandos.

Вам также может понравиться