Los 7 patrones de diseño de software más importantes

Para una inmersión profunda en el tema de los Patrones de diseño de software, consulte Patrones de diseño de software: mejores prácticas para desarrolladores, creado por C.H. Afzal, un ingeniero de software veterano con múltiples años de experiencia en Netflix, Microsoft y Oracle. Gran parte de lo siguiente se resume de su curso.

¿Por qué diseñar patrones?

Los patrones de diseño se han convertido en objeto de cierta controversia en el mundo de la programación en los últimos tiempos, en gran parte debido a su percepción de "uso excesivo" que conduce a un código que puede ser más difícil de entender y administrar.

Es importante comprender que los Patrones de diseño nunca tuvieron la intención de ser atacados por atajos para ser aplicados de manera aleatoria, "una talla única para todos" a su código. En última instancia, no hay sustituto para la capacidad genuina de resolución de problemas en ingeniería de software.

Sin embargo, el hecho es que los patrones de diseño pueden ser increíblemente útiles si se usan en las situaciones correctas y por las razones correctas. Cuando se usan estratégicamente, pueden hacer que un programador sea significativamente más eficiente al permitirles evitar reinventar la rueda proverbial, en lugar de usar métodos refinados por otros. También proporcionan un lenguaje común útil para conceptualizar problemas y soluciones repetidos cuando se discute con otros o se maneja el código en equipos más grandes.

Dicho esto, una advertencia importante es garantizar que el desarrollador entienda también el cómo y el por qué detrás de cada patrón.

Sin más preámbulos (en orden de importancia general, de mayor a menor):

Los patrones de diseño más importantes

  1. Semifallo

El patrón singleton se usa para limitar la creación de una clase a un solo objeto. Esto es beneficioso cuando se necesita un (y solo un) objeto para coordinar acciones en todo el sistema. Hay varios ejemplos de donde solo debería existir una única instancia de una clase, incluidos cachés, grupos de subprocesos y registros.

Es trivial iniciar un objeto de una clase, pero ¿cómo nos aseguramos de que solo se cree un objeto? La respuesta es hacer que el constructor sea "privado" para la clase que pretendemos definir como singleton. De esa manera, solo los miembros de la clase pueden acceder al constructor privado y nadie más.

Consideración importante: es posible subclasificar un singleton haciendo que el constructor esté protegido en lugar de privado. Esto podría ser adecuado en algunas circunstancias. Un enfoque adoptado en estos escenarios es crear un registro de singletons de las subclases y el método getInstance puede tomar un parámetro o usar una variable de entorno para devolver el singleton deseado. El registro luego mantiene una asignación de nombres de cadenas a objetos singleton, a los que se puede acceder según sea necesario.

2. Método de fábrica

Una fábrica normal produce bienes; Una fábrica de software produce objetos. Y no solo eso: lo hace sin especificar la clase exacta del objeto que se va a crear. Para lograr esto, los objetos se crean llamando a un método de fábrica en lugar de llamar a un constructor.

Por lo general, la creación de objetos en Java se realiza así:

SomeClass someClassObject = new SomeClass ();

El problema con el enfoque anterior es que el código que usa el objeto SomeClass se vuelve repentinamente dependiente de la implementación concreta de SomeClass. No hay nada de malo en usar nuevos para crear objetos, pero viene con el equipaje de acoplar estrechamente nuestro código a la clase de implementación concreta, lo que ocasionalmente puede ser problemático.

3. Estrategia

El patrón de estrategia permite agrupar algoritmos relacionados bajo una abstracción, lo que permite cambiar un algoritmo o política por otro sin modificar el cliente. En lugar de implementar directamente un algoritmo único, el código recibe instrucciones de tiempo de ejecución que especifican cuál del grupo de algoritmos ejecutar.

4. Observador

Este patrón es una dependencia de uno a muchos entre objetos, de modo que cuando un objeto cambia de estado, se notifica a todos sus dependientes. Esto normalmente se realiza llamando a uno de sus métodos.

En aras de la simplicidad, piense en lo que sucede cuando sigue a alguien en Twitter. Básicamente, le está pidiendo a Twitter que le envíe a usted (el observador) actualizaciones en Twitter de la persona (el sujeto) que siguió. El patrón consta de dos actores, el observador que está interesado en las actualizaciones y el sujeto que genera las actualizaciones.

Un sujeto puede tener muchos observadores y es una relación de uno a muchos. Sin embargo, un observador es libre de suscribirse a las actualizaciones de otros temas también. Puede suscribirse al servicio de noticias desde una página de Facebook, que sería el tema y siempre que la página tenga una nueva publicación, el suscriptor vería la nueva publicación.

Consideración clave: en el caso de muchos sujetos y pocos observadores, si cada sujeto almacena a sus observadores por separado, aumentará los costos de almacenamiento ya que algunos sujetos almacenarán al mismo observador varias veces.

5. Constructor

Como su nombre lo indica, se usa un patrón generador para construir objetos. A veces, los objetos que creamos pueden ser complejos, compuestos por varios subobjetos o requerir un proceso de construcción elaborado. El ejercicio de crear tipos complejos se puede simplificar utilizando el patrón de construcción. Un objeto compuesto o agregado es lo que generalmente construye un constructor.

Consideración clave: el patrón de construcción puede parecer similar al patrón de "fábrica abstracta", pero una diferencia es que el patrón de construcción crea un objeto paso a paso, mientras que el patrón de fábrica abstracto devuelve el objeto de una vez.

6. Adaptador

Esto permite que las clases incompatibles trabajen juntas al convertir la interfaz de una clase en otra. Piense en ello como una especie de traductor: cuando dos jefes de estado que no hablan un idioma común se encuentran, generalmente un intérprete se sienta entre los dos y traduce la conversación, lo que permite la comunicación.

Si tiene dos aplicaciones, con una salida de escisión como XML y la otra que requiere entrada JSON, necesitará un adaptador entre las dos para que funcionen sin problemas.

7. Estado

El patrón de estado encapsula los diversos estados en que puede estar una máquina y permite que un objeto altere su comportamiento cuando cambia su estado interno. La máquina o el contexto, como se le llama en el patrón de habla, pueden tomar acciones que lo impulsan a diferentes estados. Sin el uso del patrón, el código se vuelve inflexible y está lleno de condicionales if-else.

¿Quieres seguir aprendiendo?

Con los patrones de diseño de software: mejores prácticas para desarrolladores, tendrá la oportunidad de hacer más que solo leer la teoría. Podrá sumergirse profundamente en problemas reales y comprender soluciones prácticas con ejemplos de código de la vida real.

El curso se basa en el popular libro de The Gang of Four, pero se presenta en un formato interactivo y fácil de digerir. Dominará los 23 patrones de diseño famosos del libro de forma interactiva, aprenderá las aplicaciones adecuadas de los 3 tipos de patrones de diseño clave (creacional, estructural y de comportamiento) y aprenderá a incorporar estos patrones de diseño en sus propios proyectos.

Échale un vistazo ahora.

Publicado originalmente en blog.educative.io el 7 de noviembre de 2018.