¿Por qué debería saber programación concurrente?

17

La programación concurrente es bastante difícil para mí: incluso mirar una diapositiva básica me parece un desafío. Parece muy abstracto.

¿Cuáles son los beneficios de conocer bien los conceptos de programación concurrente? ¿Me ayudará en la programación regular y secuencial? Sé que es una satisfacción entender cómo funcionan nuestros programas, pero ¿qué más?

Adel
fuente
3
Creo que es un poco tópico, pero puede ser un poco tópico si editas todas las cosas personales (aunque la programación concurrente es bastante difícil para todos ) y pides los méritos técnicos concretos de los conceptos.
Yannis
1
Los beneficios deberían ser bastante obvios. Puede escribir programas que puedan aprovechar todas las mejoras de rendimiento disponibles a través de la división del trabajo que ofrece la programación concurrente. No es fácil para nadie. Es un concepto muy desafiante hoy.
Aparejo
3
No podemos ayudarlo a obtener motivación para aprender algo, pero la pregunta general sobre por qué uno debe saber sobre la concurrencia es bastante sobre el tema.
2
Sé de programación concurrente. Puedo decir que la diapositiva que proporciona no ayuda a entender. En cambio, vaya a una fiesta con filósofos que cenan .
mouviciel
1
Relájese, incluso a los más grandes les resulta difícil: informmit.com/articles/article.aspx?p=1193856
SK-logic

Respuestas:

32

Aquí hay una motivación fácil y rápido: Si desea código para nada más que los sistemas más débiles, más pequeños, que va a escribir código concurrente.

¿Quieres escribir para la nube? Las instancias de cómputo en la nube son pequeñas. No obtienes grandes, obtienes muchos pequeños. De repente, su pequeña aplicación web es una aplicación concurrente. Si lo diseñó bien, puede agregar más servidores a medida que gana clientes. De lo contrario, debe aprender cómo mientras su instancia tiene su promedio de carga vinculado.

OK, ¿quieres escribir aplicaciones de escritorio? Todo tiene una CPU de doble núcleo o más. Excepto las máquinas menos costosas. Y las personas con las máquinas menos costosas probablemente no van a gastar su software costoso, ¿verdad?

¿Quizás quieres hacer desarrollo móvil? Hola, el iPhone 4S tiene una CPU de doble núcleo. El resto no estará muy lejos.

¿Videojuegos? Xbox 360 es un sistema de múltiples CPU, y la PS3 de Sony es esencialmente un sistema de múltiples núcleos.

Simplemente no puede alejarse de la programación concurrente a menos que esté trabajando en problemas pequeños y simples.

Actualización de 2016 : La versión actual del Raspberry Pi de $ 35 se basa en un sistema de cuatro núcleos en un chip destinado a teléfonos celulares. Se han logrado avances dramáticos en IA en parte debido a la disponibilidad de tarjetas gráficas de alta gama como motores de cómputo paralelos.

ObscureRobot
fuente
1
Si bien estoy de acuerdo en principio, decir eso Everything has a dual-or-more-core-CPU. Except the least expensive machines.parece un poco absurdo. Mucha gente tiene máquinas de un solo núcleo, no porque sea barato, sino porque están contentas con lo que tienen y no ven la necesidad de actualizar. Dicho esto, pensar en términos de concurrencia también ayudará al planificador en un sistema de un solo núcleo, por lo que tampoco es un esfuerzo desperdiciado en cualquier lugar donde pueda asumir la multitarea preventiva (que es sobre cada entorno de multitarea con el que la mayoría de los desarrolladores entrarán en contacto, estos días).
un CVn
1
ok, eso es un poco exagerado, pero el nuevo hardware tiende a ser multinúcleo. No veo que eso se vaya. Por lo tanto, si hoy es un estudiante que piensa en el trabajo que realizará profesionalmente en el futuro, es seguro asumir que trabajará en sistemas multinúcleo.
ObscureRobot
Me pregunto si estoy en desacuerdo con tu respuesta tanto como tú
1
Según lo leo, hay un núcleo de similitud con lo que ambos estamos diciendo, @ acidzombie24. Estoy diciendo que un desarrollador debe saber cómo lidiar con la concurrencia porque estará en todas partes. Estás diciendo que no tienes que ser bueno en la programación concurrente siempre y cuando ... evites las trampas de los sistemas concurrentes :)
ObscureRobot
Estoy de acuerdo en que es muy útil saber acerca de la concurrencia, pero no estoy de acuerdo, solo puede alejarse de ella por "problemas pequeños y simples". Puede alejarse mucho de la concurrencia, incluso en sistemas no triviales, por ejemplo, si confía en los marcos y servidores de aplicaciones existentes. Una vez que la infraestructura está en su lugar, puedo ser un desarrollador junior que escribe nuevos servicios para una aplicación web y no sé casi NADA sobre concurrencia o paralelismo.
Andres F.
21

Desde 1970 hasta aproximadamente 2002, los procesadores duplicaron su velocidad aproximadamente cada 18 meses. Como programador, todo lo que tenía que hacer era esperar y su programa iría más rápido. El problema es que alrededor de 2002 las reglas cambiaron. Ahora no están haciendo procesadores rápidos más grandes, están haciendo procesadores más pequeños y lentos, sino que los ponen en grupos. La computadora en la que estoy trabajando ahora tiene 4 núcleos, y existen chips con hasta 8 núcleos (y 4 hilos por núcleo). Muy pronto tendremos chips con muchos más núcleos.

Entonces, si escribe un programa que no es del todo concurrente, encontrará que está usando 1 núcleo o hilo, pero el resto de la CPU está allí sin hacer nada. Entonces, si tiene 16 núcleos, 1 ejecutará su programa y los otros 15 estarán allí.

El problema con la concurrencia es que no es determinista. Es decir que no sabes exactamente en qué orden los diferentes hilos harán las cosas. Tradicionalmente, los programadores han intentado resolver esto usando bloqueos y similares. Esto ha llevado a MUCHO dolor. ¡Tener alguna forma de estado mutable al que más de un hilo puede acceder libremente es a menudo una fórmula para el dolor y las heinsebugs!

Últimamente, la tendencia ha sido pasar a lenguajes funcionales que controlen estrictamente el estado mutable. Hay dos formas básicas en que los lenguajes funcionales manejan la concurrencia. El primero es mediante el paso de mensajes. Esto es mejor demostrado por Erlang. En Erlang, en general, no hay estado compartido entre procesos. Se comunican no compartiendo memoria sino mis mensajes que pasan. Esto debería tener sentido para usted, ya que lo estamos haciendo en este momento. ¡Te envío esta información enviándote un mensaje, no recordando que se lo saqué de mi cerebro! Al cambiar al mensaje que pasa, la mayoría de los errores de bloqueo simplemente desaparecen. Además, los mensajes se pueden pasar a través de la red y dentro de un nodo.

El otro método es STM, que significa memoria transcripcional de software, presente en clojure y Haskell (y otros). En la memoria STM se comparte, pero los cambios solo se pueden realizar a través de una transacción. Como la gente de la base de datos descubrió todo esto en la década de 1970, es bastante fácil asegurarse de que lo hagamos bien.

En realidad, simplifiqué un poco, Clojure y Haskell pueden pasar mensajes, y Erlang puede hacer STM.

Descargo de responsabilidad Soy el autor de la programación de servicios web con Erlang , que saldrá a la venta en las próximas semanas.

Zachary K
fuente
1
@Zachary K: ¿existen enfoques que combinen los lenguajes funcionales con los lenguajes nativos para que las partes de computación intensiva se implementen en el idioma nativo pero proporcionen interfaces que pueda ser consumida por un servidor escrito en lenguaje funcional?
rwong
No estoy 100% seguro, pero existen Clojure y Scala en la JVM, así que ahí es donde comenzaría. Quizás eche un vistazo al marco de Akka. No lo he usado, pero escuché una charla sobre Akka hace un tiempo y parece que podría ser genial. ¡Por ahora estoy haciendo Erlang y Javascript, que me está tomando la mayor parte del tiempo!
Zachary K
1
@rwong: .NET permite a los programadores usar C # u otros lenguajes no funcionales para algunas partes de sus aplicaciones y F #, un lenguaje funcional, para otras.
Kevin
5

Porque la concurrencia puede estallar en tu cara cuando menos lo esperas ...

fortran
fuente
44
+10000000000000000000000000000000000000000
8
La concurrencia es la nueva Inquisición española [/ python] [como en: nadie espera ...]
ObscureRobot
1
@ObscureRobot dos veces más divertido! (la explicación no era necesaria :-p)
fortran
4

La primera regla de la programación concurrente es "Es difícil". La segunda regla de la programación concurrente es "¡Es. Es. Difícil" ... !!

En serio, sin embargo, hay dos enfoques comunes para la programación concurrente, multiproceso y multiprocesamiento. El procesamiento múltiple es el más fácil de comprender, ya que solo significa tener múltiples instancias de un proceso en ejecución para realizar una tarea. Esto es bastante fácil de hacer en sistemas basados ​​en Unix a través de llamadas a fork / join, pero no es tan fácil en sistemas Windows.

El subprocesamiento múltiple es probablemente el enfoque en el que la mayoría de la gente piensa cuando habla de concurrencia. No es difícil iniciar múltiples hilos dentro de una aplicación, pero el diablo está en los detalles. Debe coordinar el intercambio de datos entre subprocesos (generalmente utilizando bloqueos), lo que puede provocar un punto muerto o datos en un estado no válido. También debe comprender cómo comunicarse entre hilos utilizando conceptos como semáforos, variables condicionales, etc.

La ventaja de todo esto es que una vez que lo entiendes, puedes utilizar de manera más efectiva el hardware subyacente. En estos días es más o menos la norma que un procesador tenga múltiples núcleos. Al utilizar la programación concurrente, puede hacer que estos núcleos funcionen para usted, y su aplicación obtendrá una mejora en la velocidad.

La desventaja es que debe comenzar a pensar en cómo dividirá su aplicación en partes pequeñas que se pueden ejecutar en diferentes subprocesos. Esto es mucho más difícil de lo que parece. Además, las soluciones altamente concurrentes pueden ser incómodas para la prueba unitaria ya que el orden de ejecución es menos determinista.

En la actualidad, la mayoría de los idiomas se envían con una abstracción sobre la mayoría de las primitivas concurrentes para facilitar un poco la vida. Por ejemplo, .NET 4 se entrega con la Biblioteca de tareas paralelas que hace la vida un poco más fácil. En tierra Java tienen el paquete de concurrencia .

Sean
fuente
1
Obtiene órdenes de magnitud si huyes de las cerraduras lo más rápido posible. Usa STM o actores y todo lo que dijiste desaparece. Por supuesto, eso significa alejarse de Java a idiomas como Scala, Erlang o Clojure. (aunque yo diría que esto también es algo bueno)
Zachary K
@ Zachary: Puede ser algo bueno, pero si trabaja en una tienda .NET, por ejemplo, no es práctico. STM puede ser una opción en el futuro, pero en este momento no es una opción en los idiomas principales.
Sean
Clojure se ejecuta en .net, y hay F #. Apuesto a que también hay implementaciones de STM para C #.
Zachary K
3

Recientemente tuve una tarea muy interesante que hacer en la que el multiprocesamiento me salvó. Básicamente, tuve que hacer muchas solicitudes a unos pocos servidores separados, lidiando con cantidades muy pequeñas de datos, pero muchas solicitudes.

Trabajando con PHP, hice las cosas a la antigua usanza, y el mejor tiempo que obtuve después de algunas horas de trabajo resultó en ~ 120 segundos para ejecutar una prueba determinada (muchas solicitudes + retraso de red + sin asíncrono)

Pero eso no fue suficiente en comparación con lo que necesitaba, y después de fallar miserablemente con el multiprocesamiento de PHP, me cambié a Python.

Después de algunas horas, tenía un script de multiprocesamiento de Python que se ejecutó en 20 segundos, y después de un poco de jugar con los tiempos de espera y no. de hilos que se utilizarán, lo reduje a ~ 10 segundos .

Esto fue para un sitio web escrito al 100% en PHP, excepto un script Python de 100 líneas. Y todo funciona perfectamente.

Mi conclusión sería que, incluso si no lo ayuda en el día a día, puede encontrar situaciones en las que conocer al menos los conceptos básicos de la programación concurrente lo ayudará en gran medida.

¡Buena suerte y feliz codificación!

PD: No estoy tratando de criticar PHP, pero PHP simplemente no era la herramienta adecuada para el trabajo en cuestión.

PS2: Conocer una nueva tecnología o una nueva forma de hacer las cosas puede abrir la puerta a un mundo completamente nuevo de posibilidades.

Vlad Preda
fuente
2

Si realiza algún tipo de desarrollo web, la concurrencia entra en juego, al menos con la mayoría de los idiomas. Por ejemplo, uso spring para el desarrollo web y cada nueva solicitud viene como su propio hilo. Por lo tanto, si alguna solicitud termina accediendo a un objeto compartido, donde se puede cambiar el estado de una variable, la concurrencia es un factor muy importante y debe tenerse en cuenta. Si no es así, los datos se pueden editar de forma impredecible y se puede producir corrupción de datos. No es crítico conocer hasta el último detalle sobre la concurrencia, pero aprender las piezas a la vez es importante para comprender mejor la programación de aplicaciones web, si está trabajando en aplicaciones de escritorio, tal vez no sea tan importante a menos que necesite ejecutar múltiples hilos

programamx10
fuente
-1

Conozca la visión de los sistemas operativos. Leer el código fuente de los programadores y los controladores de dispositivos será de gran ayuda; Definitivamente son concurrentes.

jj1bdx
fuente
2
La simultaneidad para los programadores generalmente se aplica a sus propios programas que se ejecutan en varias instancias.
Intenté enfatizar que no puedes escribir tu propio programa concurrente de todos modos sin conocer los detalles del algoritmo de programación del núcleo del sistema operativo.
jj1bdx
Por qué no? Si utiliza los mecanismos de bloqueo correctamente, el algoritmo de programación del sistema operativo no es importante.