Que es más rápido-C # código inseguro o C++raw


Estoy escribiendo un programa de procesamiento de imágenes para realizar el procesamiento en tiempo real de fotogramas de vídeo. Está en C# usando el Emgu.CV biblioteca (C#) que envuelve la dll de la biblioteca OpenCV (C++no administrado). Ahora tengo que escribir mi propio algoritmo especial y tiene que ser lo más rápido posible.

Que será una implementación más rápida del algoritmo?

  1. Escribir una función 'insegura' en C #

  2. Agregar la función a la biblioteca OpenCV y llamarla a través de Emgu.CV

Supongo que C # unsafe es más lento porque pasa por el compilador JIT, pero ¿la diferencia sería significativa?

Editar:

Compilado para. NET 3.5 bajo VS2008

Author: Mysticial, 2008-11-11

10 answers

Debe ser Lo más rápido posible

Entonces estás haciendo la pregunta equivocada.

Codifíquelo en ensamblador, con diferentes versiones para cada variante de arquitectura significativa que admita.

Use como guía la salida de un buen compilador de C++ con optimización, porque probablemente conoce algunos trucos que usted no. Pero probablemente podrá pensar en algunas mejoras, porque C++ no necesariamente transmite al compilador toda la información que podría ser útil para la optimización. Por ejemplo, C++ no tiene la palabra clave C99 restrict. Aunque en ese caso en particular muchos compiladores de C++ (incluyendo MSVC) ahora lo soportan, así que úsalo cuando sea posible.

Por supuesto, si quieres decir, "Quiero que sea rápido, pero no hasta el punto de ir fuera de C# o C++", entonces la respuesta es diferente; -)

Esperaría que C# al menos se acerque al rendimiento de C++ de aspecto similar en muchos casos. Supongo, por supuesto, que el programa se ejecutará lo suficiente como para que el tiempo que toma el JIT en sí sea irrelevante, pero si estás procesando mucho video, eso parece probable. Pero también esperaría que haya ciertas cosas que si las haces en C # inseguro, serán mucho más lentas que la cosa equivalente en C++. No se cuáles son, porque toda mi experiencia de JITs está en Java en lugar de CLR. También puede haber cosas que son más lentas en C++, por ejemplo, si su algoritmo hace cualquier llamada de nuevo en el código C#.

Desafortunadamente el único la manera de estar seguro de lo cerca que está es escribir ambos y probarlos, lo que pasa por alto el punto de que escribir la versión de C++ es un montón de esfuerzo adicional. Sin embargo, es posible que pueda obtener una idea aproximada pirateando un código rápido que se aproxima al procesamiento que desea hacer, sin necesariamente hacerlo todo o hacerlo bien. Si su algoritmo va a recorrer todos los píxeles y hacer algunos FP ops por píxel, entonces hackear juntos un punto de referencia aproximado debería tomar toda la mitad de un hora.

Normalmente desaconsejaría empezar a pensar "esto tiene que ser lo más rápido posible". Los requisitos deben ser alcanzables, y por definición "tan X como sea posible" solo es alcanzable límite. Los requisitos también deben ser comprobables, y "as X as possible" no es comprobable a menos que de alguna manera sepa un máximo teórico. Un requisito más amigable es "esto necesita procesar fotogramas de video de tal y tal resolución en tiempo real en tal y tal CPU de velocidad", o " esto debe ser más rápido que el producto de nuestro principal competidor". Si la versión de C# hace eso, con un poco de sobra para tener en cuenta los problemas menores inesperados en la configuración del usuario, entonces el trabajo hecho.

 67
Author: Steve Jessop,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-10-12 13:34:21

Depende del algoritmo, la implementación, el compilador C++ y el compilador JIT. Supongo que en la mayoría de los casos la implementación de C++ será más rápida. Pero esto puede cambiar.

El compilador JIT puede optimizar su código para la plataforma en la que se ejecuta su código en lugar de un promedio para todas las plataformas en las que se puede ejecutar su código como lo hace el compilador C++. Esto es algo en lo que las versiones más nuevas del compilador JIT son cada vez más buenas y en algunos casos pueden dar una ventaja al código JITted. Tan la respuesta no es tan clara como cabría esperar. El nuevo compilador de Java hotspot hace esto muy bien, por ejemplo.

Otras situaciones en las que el código administrado puede funcionar mejor que C++ es donde necesita asignar y desasignar muchos objetos pequeños. El tiempo de ejecución de.net preasigna grandes trozos de memoria que se pueden reutilizar para que no tenga que llamar al sistema operativo cada vez que necesite asignar memoria.

No estoy seguro de que el C# inseguro funcione mucho más rápido que el C#normal. Tendrás que probar esto. demasiado.

Si quieres saber cuál es la mejor solución para tu situación tendrás que probar ambos y medir la diferencia. No creo que haya más de

 6
Author: Mendelt,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-11-11 11:20:09

C# es típicamente más lento que C++. Hay comprobaciones de tiempo de ejecución en el código administrado. Estos son los que lo hacen manejado, después de todo. C++ no tiene que comprobar si los límites de una matriz se han excedido, por ejemplo.

Desde mi experiencia, usar memoria fija ayuda mucho. Hay una nueva clase System.IO.UnmanagedMemoryAccessor en.NET 4.0 que puede ayudar en el futuro.

 6
Author: Thomas Bratt,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-11-11 12:43:07

Los idiomas no tienen una "velocidad". Depende del compilador y del código. Es posible escribir código ineficiente en cualquier idioma, y un compilador inteligente generará código casi óptimo sin importar el idioma de la fuente.

El único factor realmente inevitable en el rendimiento entre C# y C++ es que las aplicaciones de C# tienen que hacer más al inicio (cargar el.NET framework y tal vez JIT algo de código), por lo que, en igualdad de condiciones, se lanzarán un poco más lento. Después de eso, depende, y hay no hay ninguna razón fundamental por la que un idioma deba ser siempre más rápido que otro.

Tampoco conozco ninguna razón por la que C# inseguro debería ser más rápido que seguro. En general, safe es bueno porque permite al compilador hacer algunas suposiciones mucho más fuertes, por lo que safe podría ser más rápido. Pero de nuevo, depende del código que esté compilando, el compilador que esté utilizando y una docena de otros factores.

En resumen, renuncia a la idea de que puedes medir el rendimiento de un idioma. Usted un idioma nunca es "rápido" o lento". No tiene velocidad.

 5
Author: jalf,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-11-11 11:26:39

Si vas a implementar tu algoritmo de una manera estándar creo que es irrelevante. Pero algunos idiomas tienen enlaces a api o bibliotecas que pueden darle un impulso no estándar.

  1. Considere si puede usar procesamiento de GPU: nvidia y ati proporcionan los marcos CUDA y CTM y hay un esfuerzo continuo de estandarización del grupo khronos (OpenGL). Una corazonada me dice también que amd agregará al menos un núcleo de procesador de transmisión en sus futuros chips. Así que creo hay una gran promesa en esa área.

  2. Trate de ver si puede explotar las instrucciones de SSE, hay bibliotecas alrededor-la mayoría en C++ o C - que proporcionan apis útiles, consulte el sitio de Intel para bibliotecas optimizadas útiles Recuerdo "Primitivas de rendimiento de Intel" y un "Núcleo de matemáticas".

Pero en el lado de la política, incorpore su algoritmo en OpenCV para que otros también se beneficien.

 4
Author: thAAAnos,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-11-11 13:45:32

Si conoce su entorno y utiliza un buen compilador (para el procesamiento de video en Windows, el compilador Intel C++ es probablemente la mejor opción), C++ vencerá a C# por varias razones:

  • El entorno de tiempo de ejecución de C++ no tiene comprobaciones de tiempo de ejecución intrínsecas (la desventaja es que tiene libertad para explotarse). El entorno de tiempo de ejecución de C# va a tener algunas comprobaciones de cordura, al menos inicialmente.
  • Los compiladores de C++ se construyen para optimizar el código. Mientras es teóricamente posible implementar un compilador JIT de C# usando todo el voodo de optimización que usa ICC (o GCC), es dudoso que el JIT de Microsoft lo haga mejor de manera confiable. Incluso si el compilador JIT tiene estadísticas de tiempo de ejecución, eso todavía no es tan bueno como la optimización guiada por perfil en ICC o GCC.
  • Un entorno C++ le permite controlar su modelo de memoria mucho mejor. Si su aplicación llega al punto de aplastar la caché de datos o fragmentar el montón, realmente aprecie el control adicional sobre la asignación. Diablos, si puede evitar asignaciones dinámicas, ya está mucho mejor (pista: el tiempo de ejecución de malloc() o cualquier otro asignador dinámico no es determinista, y casi todos los idiomas no nativos fuerzan un uso más pesado del montón, y por lo tanto una asignación más pesada).

Si usas un compilador pobre, o si no puedes apuntar a un buen chipset, todas las apuestas están canceladas.

 2
Author: Tom Barta,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-11-26 04:11:46

Es una batalla que continuará para siempre. C versus C++ versus C # versus lo que sea. En C#, la noción de inseguro es desbloquear operaciones "peligrosas". es decir, el uso de punteros, y ser capaz de emitir a void punteros etc, como se puede en C y C++. Muy peligroso, y muy potente! Pero derrotando en lo que se basaba C#.

Encontrará que hoy en día, Microsoft ha avanzado en la dirección del rendimiento, especialmente desde el lanzamiento de. NET, y la próxima versión de. NET lo hará en realidad, admite métodos en línea, como puede hacerlo con C++. Esto aumentará el rendimiento para situaciones muy específicas. Odio que no vaya a ser una característica de c#, sino un atributo desagradable que el compilador recoge, pero no puedes tenerlo todo.

Personalmente, estoy escribiendo un juego con C# y DirectX administrado (¿por qué no XNA?? más allá del alcance de este post). Estoy usando código inseguro en situaciones gráficas, lo que provoca un guiño en la dirección de lo que otros han dicho.

Es sólo debido a que el acceso a píxeles es redículamente lento con GDI++, me impulsó a buscar alternativas. Pero en general, el compilador de c# es bastante bueno, y para comparaciones de código (puedes encontrar artículos) encontrarás que el rendimiento es muy comparable a c++. Eso no quiere decir que no haya una mejor manera de escribir el código.

Al final del día, personalmente veo C, C++ y C# como aproximadamente la misma velocidad cuando se ejecuta. Es solo que en algunas situaciones dolorosas donde quieres trabajar muy cerca del hardware subyacente o muy cerca de esos píxeles, que encontrará una ventaja notable para la multitud de C/C++.

Pero para los negocios, y la mayoría de las cosas hoy en día, C# es un verdadero contendiente, y permanecer dentro del entorno "seguro" es definitivamente una ventaja.
Al salir, puede hacer la mayoría de las cosas con código inseguro, como lo he hecho yo, y ¡vaya, he llegado a algunos extremos! Pero valió la pena? Probablemente no. Personalmente me pregunto si debería haber pensado más a lo largo las líneas de código de tiempo crítico en C++, y todas las cosas seguras orientadas a objetos en C#. ¡Pero tengo mejor rendimiento de lo que pensé que tendría!

Siempre y cuando tengas cuidado con la cantidad de llamadas interop que estás haciendo, puedes obtener lo mejor de ambos mundos. Personalmente he evitado eso, pero no se a qué costo.

Así que un enfoque que no he probado, pero me encantaría escuchar aventuras en, en realidad el uso de C++. NET para desarrollar una biblioteca en-sería más rápido que c # ' s inseguro para estas situaciones gráficas especiales? ¿Cómo se compararía eso con el código compilado nativo de C++? Ahora hay una pregunta!

Hmm..

 2
Author: Simon Miller,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-07-18 13:30:59

Estoy un poco tarde en responder, pero puedo darle algunas experiencias anecdóticas. Tuvimos algunas rutinas de multiplicación de matrices que originalmente fueron codificadas en C # usando punteros y código inseguro. Esto resultó ser un cuello de botella en nuestra aplicación y luego usamos pinning+P/Invoke para llamar a una versión en C++ de la rutina de multiplicación de matrices y obtuvimos un factor de mejora de 2. Esto fue hace un tiempo con. NET 1.1, por lo que las cosas podrían ser mejores ahora. Como otros señalan, esto prueba nada, pero fue un ejercicio interesante.

También estoy de acuerdo con thAAAnos, si el algoritmo realmente tiene que ser "lo más rápido posible" aprovechar IPL o, si debe, considerar una implementación de GPU.

 1
Author: Peter Tate,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-11-28 20:56:56

Para ser honesto, el idioma en el que lo escribes no es tan importante como los algoritmos que usas (IMO, de todos modos). Tal vez yendo a código nativo podría hacer que su aplicación sea más rápida, pero también podría hacerla más lenta depend dependería del compilador, cómo se escriben los programas, qué tipo de costos de interop incurriría si está utilizando un entorno mixto, etc. Realmente no se puede decir sin perfilarlo. (y, para el caso, ¿ha perfilado su solicitud? ¿ ¿sabes dónde está pasando el tiempo?)

Un algoritmo mejor es completamente independiente del idioma que elija.

 1
Author: user25967,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-06-10 00:40:21

Ejecutar en la CPU siempre va a ser más rápido que ejecutar en una máquina virtual en la CPU. No puedo creer que la gente esté tratando de discutir lo contrario.

Por ejemplo, tenemos un trabajo de procesamiento de imágenes bastante pesado en nuestro servidor web que está en cola. Inicialmente para que funcionara, usamos las funciones GD de PHP.

Eran lentos como el infierno. Reescribimos la funcionalidad que necesitábamos en C++.

 -7
Author: Dave,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2008-11-11 11:37:41