¿Qué es realmente más eficiente? Haskell u OCaml
benchmarking (5)
Pasé los últimos 18 meses controlando la programación funcional, comenzando con el aprendizaje de OCaml y durante algunas semanas ahora con Haskell. Ahora quiero dar el siguiente paso e implementar alguna aplicación real: un simple editor de terreno en tiempo real. He escrito numerosos motores de renderizado de terreno en tiempo real, por lo que este es un tema familiar. Y los algoritmos recursivos y las estructuras de datos utilizados parecen muy adecuados para una implementación funcional.
Al tratarse de una aplicación en tiempo real, naturalmente busco el mejor rendimiento que pueda obtener. Ahora, algunos (en mi humilde opinión bastante molestos) proponente de OCaml son bastante frecuentes en contra de que Haskell sea lento en comparación con OCaml o F #. Pero de acuerdo con The Computer Language Benchmarks Game, Haskell a menudo supera a OCaml, aunque solo por fracciones pequeñas, sigue existiendo el problema de que este benchmark solo toma muestras muy específicas.
Lo correcto sería, por supuesto, implementar el programa en ambos idiomas y compararlo, pero simplemente no quiero hacer doble trabajo.
¿Pero tal vez otras personas hicieron aplicaciones comparables en OCaml y Haskell y dieron algunas cifras?
He escrito numerosos motores de renderizado de terreno en tiempo real, por lo que este es un tema familiar.
Lo suficientemente familiar como para saber dónde se gastará la mayor parte del tiempo?
Si es así, entonces quizás puedas escribir el código solo para esa parte en diferentes idiomas y comparar.
Pero de acuerdo con The Computer Language Benchmarks Game, Haskell a menudo vence a OCaml, aunque solo por fracciones pequeñas, sigue existiendo el problema de que este benchmark solo toma muestras muy específicas.
El juego de puntos de referencia informa 4 series de resultados, un núcleo y cuatro núcleos , Ubuntu de 32 o 64 bits, y es posible que los programas de referencia OCaml o Haskell tengan un mejor o peor rendimiento según la plataforma.
Todo lo que un punto de referencia puede hacer es tomar muestras muy específicas, y por supuesto, debe ignorar las comparaciones en tareas que son diferentes a las que se dedicarán a la aplicación: ¿aritmética de enteros grandes? ¿Regex? ¿instrumentos de cuerda? - y mira las comparaciones que son más parecidas a lo que pretendes hacer.
Con la ayuda de dos colegas muy inteligentes, escribí una biblioteca de optimización de flujo de datos en Objective Caml y Haskell. La versión de Haskell es un poco más polimórfica, tiene más comprobaciones de tipo en tiempo de compilación y, por lo tanto, tiene menos comprobaciones en tiempo de ejecución. La versión de OCaml usa un estado mutable para acumular datos de flujo de datos, lo que podría ser más rápido o más lento esta semana, dependiendo de la fase de la luna. El hecho clave es que en sus aplicaciones previstas, ambas bibliotecas son tan rápidas que no vale la pena perder el tiempo . Es decir, en los compiladores respectivos ( C rápido y GHC ), se dedica tan poco tiempo a la optimización del flujo de datos que no vale la pena mejorar el código.
Benchmarking es el infierno.
En base a todos los datos que he visto, son más o menos comparables. El código que escriba hará una gran diferencia que el idioma en sí.
Interesante pregunta. Este renderizador de terreno de todo el planeta fue uno de los últimos programas que escribí en C ++ antes de migrar a OCaml. Mirando hacia atrás, ese programa hubiera sido mucho más fácil de escribir en OCaml que en C ++. Haskell debería hacerlo comparablemente fácil, pero los programas suelen ser mucho más difíciles de optimizar en Haskell. En teoría, Haskell tiene mejor soporte para multinúcleos pero, en la práctica, incluso los expertos rara vez obtienen resultados decentes usando Haskell para programación paralela.
Además, para las aplicaciones en tiempo real también querrá tiempos de pausa bajos del recolector de basura. OCaml tiene un buen colector incremental que da como resultado pocas pausas por encima de 30 ms, pero, IIRC, GHC tiene un colector de dejar el mundo que incurre en pausas arbitrariamente largas.
Supongo que estás usando Linux o F # sería una elección mucho mejor que OCaml o Haskell.
EDITAR: Si quieres estudiar el tiroteo, asegúrate de leer el código fuente. También puede encontrar las páginas wiki de Haskell interesantes.
Según todas las versiones, tanto OCaml como Haskell tienen compiladores y tiempos de ejecución lo suficientemente efectivos para casi cualquier cosa. Escoger entre ellos sobre la base de puro rendimiento me parece tonto. Has llegado hasta aquí, alejándote de los lenguajes obviamente de bajo nivel y rendimiento (C, C ++, etc.) en nombre de un código más claro, más conciso, más expresivo y de más alto nivel. Entonces, ¿por qué, cuando las diferencias de rendimiento involucradas son mucho más pequeñas, cambie a ese criterio ahora?
Me gustaría ir con algunos criterios más amplios: si quieres un paralelismo generalizado, entonces Haskell es la mejor opción. Si quieres una mutación genuinamente penetrante, entonces OCaml es mejor.
Si solo quieres un paralelismo muy grueso, y tienes la intención de mantenerte con estructuras funcionales en su mayoría, escoge basado en otra cosa, como sintaxis (creo que Haskell es mucho más agradable aquí, pero eso es subjetivo) o librerías disponibles (Haskell gana en cantidad / disponibilidad, pero OCaml podría superarlo en el departamento de gráficos, no obstante).
No creo que vayas a equivocar de ninguna manera