Patrón de diseño de Python

Visión general

El desarrollo de software moderno debe abordar requisitos comerciales complejos. También debe tener en cuenta factores como la futura extensibilidad y mantenibilidad. Un buen diseño de un sistema de software es vital para lograr estos objetivos. Los patrones de diseño juegan un papel importante en tales sistemas.

Para comprender el patrón de diseño, consideremos el siguiente ejemplo:

  • El diseño de cada automóvil sigue un patrón de diseño básico, cuatro ruedas, volante, el sistema de transmisión central como acelerador-freno-embrague, etc.

Por lo tanto, todas las cosas construidas / producidas repetidamente, inevitablemente seguirán un patrón en su diseño ... coches, bicicletas, pizza, cajeros automáticos, lo que sea ... incluso su sofá cama.

Los diseños que casi se han convertido en una forma estándar de codificar alguna lógica / mecanismo / técnica en el software, por lo tanto, se conocen o se estudian como Patrones de diseño de software.

¿Por qué es importante el patrón de diseño?

Los beneficios de usar patrones de diseño son:

  • Le ayuda a resolver problemas de diseño habituales mediante un enfoque probado.

  • No hay ambigüedad en el entendimiento ya que están bien documentados.

  • Reducir el tiempo total de desarrollo.

  • Le ayuda a lidiar con futuras extensiones y modificaciones con más facilidad que de otra manera.

  • Puede reducir los errores en el sistema ya que son soluciones comprobadas a problemas comunes.

Clasificación de patrones de diseño

Los patrones de diseño de GoF (Gang of Four) se clasifican en tres categorías: creacionales, estructurales y de comportamiento.

Patrones de creación

Los patrones de diseño de creación separan la lógica de creación de objetos del resto del sistema. En lugar de que usted cree objetos, los patrones de creación los crea por usted. Los patrones de creación incluyen Abstract Factory, Builder, Factory Method, Prototype y Singleton.

Los patrones de creación no se usan comúnmente en Python debido a la naturaleza dinámica del lenguaje. Además, el lenguaje en sí nos proporciona toda la flexibilidad que necesitamos para crear de una manera lo suficientemente elegante, rara vez necesitamos implementar algo en la parte superior, como singleton o Factory.

Además, estos patrones proporcionan una forma de crear objetos mientras se oculta la lógica de creación, en lugar de instanciar objetos directamente utilizando un nuevo operador.

Patrones estructurales

A veces, en lugar de empezar desde cero, es necesario construir estructuras más grandes utilizando un conjunto de clases existente. Ahí es donde los patrones de clases estructurales usan la herencia para construir una nueva estructura. Los patrones de objetos estructurales utilizan la composición / agregación para obtener una nueva funcionalidad. Adaptador, Puente, Compuesto, Decorador, Fachada, Peso mosca y Proxy son Patrones Estructurales. Ofrecen las mejores formas de organizar la jerarquía de clases.

Patrones de comportamiento

Los patrones de comportamiento ofrecen las mejores formas de manejar la comunicación entre objetos. Los patrones que se incluyen en estas categorías son: visitante, cadena de responsabilidad, comando, intérprete, iterador, mediador, recuerdo, observador, estado, estrategia y método de plantilla son patrones de comportamiento.

Debido a que representan el comportamiento de un sistema, generalmente se usan para describir la funcionalidad de los sistemas de software.

Patrones de diseño de uso común

único

Es uno de los patrones de diseño más controvertidos y famosos. Se utiliza en lenguajes excesivamente orientados a objetos y es una parte vital de la programación tradicional orientada a objetos.

El patrón Singleton se utiliza para,

  • Cuando es necesario implementar el registro. La instancia del registrador es compartida por todos los componentes del sistema.

  • Los archivos de configuración utilizan esto porque la caché de información debe ser mantenida y compartida por todos los componentes del sistema.

  • Gestionar una conexión a una base de datos.

Aquí está el diagrama UML,

class Logger(object):
   def __new__(cls, *args, **kwargs):
      if not hasattr(cls, '_logger'):
      cls._logger = super(Logger, cls).__new__(cls, *args, **kwargs)
return cls._logger

En este ejemplo, Logger es un Singleton.

Cuando se llama a __new__, normalmente construye una nueva instancia de esa clase. Cuando lo anulamos, primero verificamos si nuestra instancia de singleton se ha creado o no. Si no, lo creamos usando una super llamada. Por lo tanto, cada vez que llamamos al constructor en Logger, siempre obtenemos exactamente la misma instancia.

>>>
>>> obj1 = Logger()
>>> obj2 = Logger()
>>> obj1 == obj2
True
>>>
>>> obj1
<__main__.Logger object at 0x03224090>
>>> obj2
<__main__.Logger object at 0x03224090>