Cómo aprender qué es la buena arquitectura

Una buena arquitectura consiste en optimizar tres requisitos:

  1. Los usuarios deben estar satisfechos con el rendimiento, la usabilidad y la solidez.
  2. Los desarrolladores actuales deben poder leer / escribir código de manera eficiente y sin errores.
  3. Los futuros desarrolladores deben poder extender y mejorar el código fácilmente.

Desafortunadamente, es casi imposible satisfacer los tres requisitos simultáneamente. A veces necesitamos aumentar la complejidad para obtener las funciones del usuario. O a veces necesitamos sacrificar la extensibilidad para que sea más fácil para los desarrolladores. Y los tres tienden a sacrificarse cuando hay restricciones de recursos impuestas por el negocio.

No existe un algoritmo simple para llegar a una buena arquitectura porque las compensaciones entre los tres requisitos dependen de los detalles del proyecto. La experiencia y la práctica son las únicas formas de desarrollar la intuición para hacer las compensaciones correctas. Así que no importa lo que haga, practique en sus propios proyectos e intente evaluar la arquitectura resultante con respecto a los tres requisitos anteriores.

Déjame pasar por un ejemplo:

Probablemente estés familiarizado con el juego Asteroides . Es un juego simple en el que pilotas una nave espacial (en el medio) y disparas a los asteroides. Si un asteroide te golpea, mueres. Pero si le disparas a un asteroide, se divide en asteroides más pequeños.

Intentemos implementar este juego en un lenguaje típico orientado a objetos. ¿Qué clases definirías? ¿Cuáles son sus métodos? ¿Cómo interactuarían? Esta es una gran parte de la definición de la arquitectura.

Podríamos ingenuamente comenzar con dos clases: una para el barco ( CShip ) y otra para los asteroides ( CAsteroid ). Cada clase es responsable de pintarse y actualizar su movimiento. Y, por supuesto, cada uno podría descender polimórficamente de la clase abstracta CSpaceObject .

Hasta ahora todo bien, pero ¿y las balas? ¿Cómo representamos las balas? ¿Debería cada viñeta ser su propio objeto (una clase CBullet )? ¿Debería el jugador enviar un seguimiento de sus propias balas? ¿Debería haber una sola clase para rastrear todas las balas? ¿Cuáles son los pros y los contras?

  • Si las viñetas son su propio objeto, entonces la ventaja es que podemos implementar más fácilmente diferentes tipos de viñetas. Pero la desventaja podría ser el rendimiento: los objetos pueden ser caros.
  • Si incluimos balas como parte de la nave, entonces podríamos simplificar la programación (encapsular balas en un lugar), pero podríamos tener dificultades si decidimos más tarde que otros tipos de objetos también disparan balas.
  • Si tenemos una sola clase para rastrear todas las viñetas, podríamos mejorar el rendimiento, pero podríamos aumentar la complejidad del desarrollador. Por ejemplo, las pruebas de colisión se vuelven más complicadas si algunas cosas son objetos separados y otras no.

Para este proyecto en particular, implementaría cada viñeta como un objeto separado (CBullet descendiendo de CSpaceObject). Pero, ¿qué pasaría si este fuera un juego multijugador masivo con cientos de jugadores disparando balas? ¿Funcionaría la misma arquitectura? Tal vez no.

Considere la prueba de colisión. Imagine que comenzamos con una lista de todos los CSpaceObjects , que incluye barco, asteroides y balas. Podemos recorrer cada objeto y ver si está colisionando con cualquier otro objeto. Si es así, llamamos a un método para resolver la colisión. Si un asteroide golpea a un asteroide, no hacemos nada. Pero si una bala golpea un asteroide, lo rompemos.

Esta es una arquitectura simple y extensible. ¿Pero funcionará? Para n objetos necesitamos hacer [( n – 1) * n ] / 2 comparaciones. Para 100 objetos, eso es casi 5,000 comparaciones. ¡Para 1,000 objetos, es medio millón de comparaciones! Claramente esto no escalará demasiado lejos.

Podemos mejorar esto observando que estamos haciendo pruebas de colisión innecesarias. No sucede nada cuando un asteroide golpea a un asteroide, entonces, ¿por qué hacer pruebas de colisión? Pero eso significa que ya no podemos tratar a todos nuestros objetos por igual. En lugar de tener una gran lista de todos los objetos, quizás necesitemos diferentes listas para cada tipo de objeto.

Incluso en este sencillo ejemplo, puede ver la tensión entre extensibilidad, complejidad y rendimiento. Si queremos crear nuevos tipos de objetos (barco enemigo, agujeros de gusano, lo que sea), queremos que el código principal trate los objetos genéricamente y mantenga las diferencias en la implementación.

Pero si necesitamos soportar miles de objetos, necesitamos separar diferentes tipos de objetos y tratarlos de manera diferente, o crear estructuras de datos adicionales (por ejemplo, árboles de partición de espacio binario) para manejar las colisiones de manera eficiente. De cualquier manera estamos agregando más complejidad.

Ser bueno en arquitectura significa prever esta tensión desde el principio. Nunca podrá predecir el futuro, pero tener en cuenta este tipo de preguntas desde el principio podría ayudarlo a crear una arquitectura duradera.

Siempre es agradable ver a alguien que sabe lo que no sabe y se propone aprender cosas de forma proactiva.

En primer lugar, tenga en cuenta la distinción entre arquitectura de sistema y arquitectura de software:

  • Arquitectura del sistema: concepto de operaciones (p. Ej., Casos y escenarios de uso), entorno operativo (a dónde va el equipo: usuarios, servidores de terminales, sensores de E / S especializados), funciones de alto nivel, cómo se distribuyen las funciones en el hardware, flujo de datos , flujo de control, componentes principales (p. ej., DBMS), módulos e interfaces principales, entorno de tiempo de ejecución (p. ej., sistema operativo), mecanismos de confiabilidad / disponibilidad (p. ej., replicación, conmutación por error), concepto de mantenimiento, esencialmente el panorama general.
  • Arquitectura de software: cómo se organiza el software, particularmente en servidores individuales. Funciones principales, componentes (de nuevo, p. Ej., DBMS), módulos, arquitectura de datos (p. Ej., Definiciones de tablas), estándares de codificación (incluidas pruebas y documentación).
  • Y están los problemas paralelos de los procesos de gestión e integración: definiciones de lanzamiento, control de configuración, prueba de módulo, prueba de integración e integración, empaquetado, lanzamiento, mantenimiento y actualización. Procese cosas como ágil vs. cascada vs. híbrido, integración continua, DevOps.

Ahora … como desarrollador junior, la mayoría de estos deben ser definidos por el líder técnico, o el arquitecto, y el gerente del proyecto, o como un esfuerzo de equipo acurrucado alrededor de una pizarra, respaldada por una cadena de herramientas que impone algún proceso. Haga muchas preguntas, no espere muchos comentarios. A medida que madures en la profesión, aprenderás mucho de estas cosas y se espera que asumas responsabilidades más amplias y profundas, hasta que tú también puedas hacer estas cosas y asumir un papel de liderazgo.

Mientras tanto, puedes aprender algo de esto a través del estudio (recomiendo los libros de Andrew Tanenbaum). Tal vez mire Open Courseware para algún material.

También se puede encontrar mucha documentación sobre cómo se construyen varios sistemas, por ejemplo, google “slideshare de arquitectura de Facebook” y encontrará muchas presentaciones (y funciona para muchos sistemas grandes). http://Highscaleability.com también es una buena fuente (y paga uno o dos dólares al mes a través de su página de patreon). Para algunos de los principales proyectos de código abierto (por ejemplo, Apache, Postfix, kernel de Linux, algunas distribuciones de Linux, Firefox) puede encontrar información similarmente detallada sobre arquitectura de software (quizás intente sustituir “arquitectura” por “componentes internos”). También busque en Google “devops” y eche un vistazo a devops.com.

Espero que esto ayude.

Primero debe asegurarse de comprender qué arquitectura es en el contexto del software. Esto puede parecer una tontería, pero mucha gente está confundida acerca de esto, incluso las personas con el título de ‘arquitecto’. En realidad, no es una noción muy bien definida y se confunde con otros conceptos y se califica (‘red’, ‘sistema’, ‘aplicación’, ‘servicio’, …) A menudo aquí la gente dice “tenemos una arquitectura .NET” o “nuestra arquitectura es JEE” o algo así. Son un poco como decir que mi casa tiene una ‘arquitectura de ladrillo y madera’. La arquitectura es más abstracta que las herramientas y los lenguajes que usa.

Una vez que tienes eso, evaluar la arquitectura se vuelve mucho más fácil. Necesitas estudiar y trabajar con arquitecturas. Este es uno de los beneficios de trabajar en equipo con más personas mayores. ¿Qué funciona, qué no? ¿La estructura del sistema está construida porque se ajusta al problema o es así debido a las licencias de software (sí, hay arquitecturas basadas en licencias, que es una de las principales razones por las que el código abierto está ganando). Algunas arquitecturas existen porque “esa es la forma en que nosotros siempre lo he hecho ”. Si no entiende por qué las cosas son de cierta manera, haga preguntas. Si su equipo no quiere explicárselo, busque un nuevo equipo.

En definitiva, la arquitectura es un conjunto de opciones sobre diseño. La arquitectura es diseñar como la estrategia es táctica. Una buena arquitectura hace que la creación de software sea más fácil y / o más efectiva. Una mala arquitectura hace que sea difícil y / o ineficaz. Tomará tiempo, así que no seas duro contigo mismo. El hecho de que pregunte de esta manera es una buena señal de que probablemente esté bien encaminado.

Aprender una buena arquitectura es un poco como aprender a ser un buen artista. Dejame explicar.

No solo hay formas de arte muy diferentes (pintar, esculpir, tocar música, escribir novelas y hacer películas, por nombrar algunas), sino que dentro de estas formas hay estilos muy diferentes (expresionismo, impresionismo, cubismo, etc.) .

Ser un gran artista requiere años de dedicación y disciplina. Requiere experimentar con diferentes estilos y realmente encontrar el que mejor se adapte a usted.

Así es la arquitectura de software. Hay muchos diseños de arquitectura diferentes (microservicios, SOA, MV *, etc.) y con una búsqueda rápida y sesgada de Google (“¿por qué los microservicios son malos?”, “Los microservicios son geniales”) puede encontrar personas en ambos lados de la cerca para cualquier Elección de la arquitectura.

Lo que esto me dice es que todo se reduce a la preferencia personal por el problema en cuestión. Esta experiencia no se obtiene de la noche a la mañana y se espera que un desarrollador Junior no tenga una sólida formación en opciones de diseño de arquitectura.

En cuanto a aprender arquitectura, recomendaría lo siguiente como punto de partida para el diseño orientado a objetos:

  • Código limpio: un manual de artesanía de software ágil: Robert C. Martin:
  • Tio bob videos
  • martinfowler.com

En resumen, la arquitectura de software es como el arte. Se necesita tiempo y experiencia para dominar.

Te dejo con una cita.

Miré mi mano derecha, la mano con la que pinté. Había poder en esa mano. Poder para crear y destruir. Poder para traer placer y dolor. Poder para divertir y horrorizar. Había en esa mano lo demoníaco y lo divino al mismo tiempo. Lo demoníaco y lo divino eran dos aspectos de la misma fuerza. La creación fue demoníaca y divina. La creatividad era demoníaca y divina. Yo era demoníaco y divino.

Chaim Potok, mi nombre es Asher Lev

Una buena solución para esto cuando recién está comenzando es descubrir lo que otras personas REALMENTE están haciendo, y aprender eso. Los microservicios, la arquitectura orientada al servicio y los patrones de estilo React, incluido el modelo Actor, son buenos ejemplos de esto (y el modelo Actor específicamente le ahorrará muchas canas).

En el futuro, su experiencia con lo que SABE le dará un lugar para ingresar a los lugares donde no está familiarizado, o al menos proporcionará un camino. Además, una vez que haya aprendido los conceptos básicos y haya sobrevivido a sus primeros problemas / productos principales, comenzará a tener una mejor idea de cuáles son algunos de los problemas reales de la arquitectura de software.

Una vez que hayas llegado a este punto, estarás en algún lugar del espectro entre “uno de los niños geniales” y “veterano cínico”, pero solo por aprender un punto de arquitectura te doy la siguiente advertencia. Aprenda lo que la gente está REALMENTE usando y descubra cuáles son los pros y los contras de ese enfoque. De lo contrario, solo serás otra groupie escuchando lo que digan algunos oradores sobre alguna nueva pieza de tecnología que se supone que “cambia todo”, pero que en realidad no soluciona ninguno de los inconvenientes mencionados anteriormente, a costa de muchos de los profesionales. . Esas “piezas geniales de tecnología” rara vez se convierten en algo importante, mientras que el proyecto menos obvio que resuelve un problema importante en su espacio puede convertirse en algo enorme y convertirlo en el héroe del proyecto en algún momento.

La buena arquitectura mejora la vida de las personas que utilizarán y se verán afectadas por su creación. Ese debería ser tu objetivo principal. ‘Personas’ incluye usuarios, clientes, soporte y usted también.

Comience con una lista de las personas que afectará el diseño. Podrías usar un mapa simple de tenedores de apuestas. Recuerde incluir desarrolladores en una forma de desarrollo de operaciones; Su valor es enorme. Luego, asegúrese de comprender a su gente y sus requisitos.

Una vez que comprenda a su gente y al negocio que está implementando, puede ver las herramientas, patrones, etc. y decidir qué satisface mejor las necesidades de su gente.

La buena arquitectura no se trata de qué herramientas utilizas; se trata de su idoneidad para la mano de casos de uso y cómo los aplica para mejorar la vida de su gente.

Buena suerte te deseo lo mejor.

Una buena manera de aprender a hacer una buena arquitectura es pararse sobre los hombros de gigantes. Aprenda y use patrones en su trabajo: patrones de arquitectura, patrones de diseño (patrones de arquitectura empresarial, patrones de diseño, patrones de arquitectura en la nube son libros extremadamente beneficiosos en mi experiencia). Además, siga aprendiendo nuevas tecnologías para poder usarlas cuando sea apropiado. Por último, pero no menos importante, conozca la experiencia del usuario.

Simplemente hágalo: a medida que resuelve problemas cada vez más grandes, puede usar lo que aprendió y ganar experiencia y reputación al analizar los requisitos, diseñar soluciones, estimarlos y desarrollarlos con éxito. Buena suerte.

Creo que podría estar mezclando entre arquitectura de software y diseño de software.

La arquitectura del software se centra en la estructura de alto nivel de su sistema, como la infraestructura de la aplicación, teniendo en cuenta los requisitos operativos y técnicos.

El diseño de software, por otro lado, se preocupa por organizar su código y el alcance de las Clases, métodos y módulos.

Aquí hay un artículo que te contará más

More Interesting

Los desarrolladores que respeto han recomendado de forma independiente Meteor.js, la pila Mean y React para desarrollar el prototipo de nuestra startup. ¿Cómo se comparan y cuáles son las diferencias clave que un CEO debería entender?

Si el desarrollo de software es difícil, ¿por qué es difícil?

Obtuve admisiones de UW-Tacoma y la Universidad de Santa Clara para MS en CS y SE, respectivamente. ¿Cuál debería elegir?

¿Cómo se dividen las responsabilidades entre las distintas oficinas de Spotify?

¿Hack Reactor sería útil para un europeo que intenta conseguir un trabajo en Londres / Berlín / Barcelona (ya que no puedo en los EE. UU. Por problemas de visa)?

¿Cuáles son algunos proyectos de software que incluyen álgebra lineal, cálculo y otras matemáticas incluidas en CS?

¿Cuánto costaría obtener una plataforma Zomato o Foursquare-esque construida desde cero?

¿Qué sistemas de aprendizaje automático has ayudado a construir? ¿Cuáles fueron los mayores desafíos que usted y su equipo enfrentaron?

Con el auge de las redes definidas por software, ¿tiene sentido financiero continuar buscando la certificación de Cisco?

¿Cuáles son los pros y los contras de la ingeniería eléctrica, mecánica y de software?

¿Cuáles son ejemplos de errores de visión por computadora relacionados con la raza?

¿Cómo se suele mantener en secreto el código fuente?

¿Por qué los ingenieros continúan adoptando idiomas que no están estrictamente escritos?

¿Cuáles son algunas buenas maneras de hacer un seguimiento de la deuda técnica?

¿Podría el desarrollo de software como se practica comúnmente beneficiarse de una mayor división del trabajo?