Algoritmos y Programación III 7. Diseño, primeros patrones, MVC Carlos Fontela, 2006
Temario Diseño OO y patrones Presentación de patrones de uso habitual Iterador Factory Method Template Method MVC y Observador
Qué es diseño Es el “cómo” del desarrollo Fase más ingenieril del desarrollo de software Lástima que se lo llame “arquitectura” Concebir una solución para un problema Entre el “qué” de los requerimientos y el producto terminado Propósito: crear una estructura interna clara y lo más simple posible
Patrones Solución exitosa de un problema que aparece con frecuencia “Alguien ya ha resuelto nuestros problemas” Patrones de diseño Para problemas de diseño Patrones de programación Algoritmos “con nombre” Métodos de ordenamiento, búsqueda Incluyen el algoritmo y una estructura de datos
Uso de patrones Enseñanza Aplicación en distintos contextos Comprensión de partes de un sistema Comunicación con un vocabulario común Hay en otras ingenierías
Qué diseñamos Despliegue en hardware Subsistemas o componentes de software y sus interacciones Integración con otros sistemas Interfaz de usuario Estructuras de datos Algoritmos Definiciones tecnológicas Plataforma, lenguaje, base de datos, etc.
Diseño de IU O Diseño externo Usabilidad y demás Ver diapositivas en sitio web ¡Pero verlas!
Diseño interno Arquitectura de componentes Arquitectura de despliegue Arquitectura de conectividad Protocolos y dispositivos a usar Diseño de datos Estructura de las bases de datos y la persistencia Software Lenguajes, herramientas y nomenclatura que se van a utilizar en la programación
Diseño de clases Clases de diseño Clases de implementación Describen conceptos de alto nivel Pertenecen al dominio de la solución Clases de implementación Surgen por necesidades algorítmicas, como un tipo de vector o árbol Para encontrarlas se aplican los conocimientos de algoritmos y estructuras de datos
Patrones: creación de objetos Veamos Iterator i = v.iterator(); while (i.hasNext()) { ... i.next(); ... } ¿Por qué no hacemos: Iterator i = new ... ? Iterator es una interfaz ¿Dónde está la clase? ¿Ventajas?
Iterador en Java
Iterador: consecuencias (I) Simplifica la interfaz de la colección No hay recorridos No expone la estructura de la colección Cumple el principio de Única Responsabilidad Mantiene alta la cohesión
Iterador: consecuencias (II) Soporte de recorridos diferentes O simultáneos Cambiando la clase de iterador No en Java, sí en C++
Iterador: implementación Control externo Cliente maneja el iterador mediante el método next() Muy flexible Control interno Iterador opera sobre los elementos, y controla el proceso Hay que decirle qué operación aplicar a los elementos Uso muy sencillo, implementación compleja
Iterador como patrón La interfaz java.util.Iterator es muy útil Pero se puede extender si se desea También hay iteradores en otros lenguajes Pero si no los hubiera se podrían implementar Como cualquier patrón de diseño
Iterador: UML
Factory Method El caso de iterator() en Java Un método que crea instancias cuyo tipo es una interfaz o una clase abstracta Se mantiene una jerarquía de clases creadoras paralela a la jerarquía de clases a crear
Template Method: polimorfismo Template Method es el uso crudo del polimorfismo Se basa en encapsular trozos de algoritmos Se lo llama también Application Framework: ¿se ve por qué? Ejemplo conocido: clase Thread ¿Por qué redefinimos run() e invocamos a start()?
Template method: UML
Template Method: varios (I) Los métodos a redefinir pueden ser abstractos en la clase plantilla O ser simples ganchos (“hooks”) con una implementación vacía o por defecto El método plantilla debería ser final Controla la lógica del algoritmo Es un marco o framework Los cambios deberían afectar solamente a los métodos redefinibles, que son los que definen los detalles
Template Method: varios (II) La clase plantilla delega en subclases la implementación de los detalles Brinda un marco general, esqueleto o armazón Decide cuándo y cómo utilizar las clases descendientes Granularidad => Flexibilidad Pero más difícil de implementar Salvo que se usen implementaciones por defecto
Template Method: usos Applets de Java Arrays.sort (Comparable[]) Muchos puntos de extensión, con implementaciones por defecto Métodos init(), start(), destroy(), etc. Arrays.sort (Comparable[]) Se debe definir compareTo() Pero no mediante herencia
Patrones: principios Encapsular lo que varía Preferir la composición a la herencia Programar usando interfaces, no implementaciones Bajo acoplamiento en la interacción entre objetos Mantener las clases abiertas para extensión y cerradas para modificación Una sola responsabilidad por clase
Diseño de arquitectura: MVC Se suele combinar con otros Bueno en aplicaciones de mucha IU Ventajas Facilitar cambios Muchas vistas por cada modelo
Observador: presentación (I) Paradigma de publicador - suscriptor. Para manejo de eventos Para MVC Para mensajería Hay dos objetos: Observador (pueden ser varios) Observado o sujeto Cambios en el estado de Observado provocan cambios en Observador
Observador: uso
Observador: estructura
Observador: consecuencias Bajo acoplamiento entre sujeto y observadores El sujeto no se preocupa de los observadores Ni cambia si se registran observadores de tipos diferentes Lo único que sabe es que implementan una determinada interfaz Los observadores se suscriben y desuscriben libremente a una lista de referencias Soporte de broadcasting Agregado y remoción dinámica de observadores
Observador: implementación Lo típico Guardar lista de observadores en sujeto Actualizaciones se materializan al cambiar estado del sujeto Posiblemente provoque muchos update() Ojo Referencias colgadas en lenguajes sin recolección de basura
Observador: variantes (I) Modelo “push” Sujeto envía toda la info que requieren los observadores Mayor acoplamiento: provoca una interfaz de observador específica Se envía información detallada, sin importar la incumbencia para los observadores
Observador: variantes (II) Modelo “pull” Sujeto no envía info, sólo notifica Observadores consultan luego lo que les interesa Puede ser ineficiente Bien desacoplado Modelo con eventos Se registran observadores sólo para ciertos eventos o temas (uno o más)
Observador en java.util (I)
Observador en java.util (II) Definir una clase descendiente de Observable (que es una clase), para hacer de sujeto: que ante determinados cambios, invoque los métodos setChanged y notifyObservers Si no se llamó a setChanged, notifyObservers no invoca los update En general los métodos de Observable no se redefinen Construir una clase que implemente Observer, implementando el método update
Observador en java.util (III) ¡Pero Observable es una clase! Y Java admite herencia simple Imposible extender un sujeto de otra clase de dominio Tampoco se puede implementar los sujetos de otra manera que no sea la de java.util setChanged es protegido Sólo puedo implementarlo en subclases No puedo utilizar composición java.util.Observable no es muy útil Hay alternativas en JavaBeans y en AWT
Resumen El diseño ha sido revalorizado con la OO Incluye diseño de arquitecturas y de clases Diseño debe mantenerse sencillo y claro Observador Desacopla un sujeto observado de observadores MVC Desacopla vista, modelo y controlador
Bibliografía La Web UML y patrones Craig Larman Orientación a objetos con Java y UML Carlos Fontela Enterprise Solution Patterns Using Microsoft .NET En MSDN, Patterns and Practices
Qué sigue Diseño de interfaces de usuario Patrones de diseño Ver en la web ¡verlo! Patrones de diseño Vuelta a programación Concurrencia Buen código OO Aplicaciones distribuidas e integración de aplicaciones
Muchas Gracias. Carlos Fontela, 2006