¿Por qué sería posible que Java fuera más rápido que C ++?

78

A veces Java supera a C ++ en los puntos de referencia. Por supuesto, a veces C ++ supera.

Vea los siguientes enlaces:

Pero, ¿cómo es esto posible? Me sorprende que el código de bytes interpretado pueda ser más rápido que un lenguaje compilado.

¿Alguien puede explicar? Gracias!

    
pregunta Deets McGeets 26.09.2011 - 06:47

15 respuestas

107

En primer lugar, la mayoría de las JVM incluyen un compilador, por lo que el "bytecode interpretado" es bastante raro (al menos en el código de referencia), no es tan raro en la vida real, donde su código suele ser más que unos pocos bucles triviales que se obtienen. repetido extremadamente a menudo).

Segundo, un buen número de los puntos de referencia involucrados parecen estar bastante sesgados (ya sea por intención o por incompetencia, realmente no puedo decir). Solo por ejemplo, hace años miré algunos de los códigos fuente vinculados a uno de los enlaces que publicaste. Tenía código como este:

  init0 = (int*)calloc(max_x,sizeof(int));
  init1 = (int*)calloc(max_x,sizeof(int));
  init2 = (int*)calloc(max_x,sizeof(int));
  for (x=0; x<max_x; x++) {
    init2[x] = 0;
    init1[x] = 0;
    init0[x] = 0;
  }

Como calloc proporciona memoria que ya está puesta a cero, el uso del bucle for para ponerlo en cero nuevamente es obviamente inútil. Esto fue seguido (si la memoria sirve) llenando la memoria con otros datos de todos modos (y no dependía de que se pusiera a cero), por lo que toda la reducción a cero era completamente innecesaria de todos modos. Reemplazar el código de arriba con un simple malloc (como cualquier persona sensata hubiera usado para comenzar) mejoró la velocidad de la versión de C ++ lo suficiente como para vencer a la versión de Java (por un margen bastante amplio, si la memoria sirve).

Considere (para otro ejemplo) el methcall benchmark usado en la entrada del blog en su último enlace. A pesar del nombre (y cómo podrían verse las cosas), la versión en C ++ de esto no realmente mide mucho sobre la sobrecarga de llamadas a métodos. La parte del código que resulta crítica está en la clase Toggle:

class Toggle {
public:
    Toggle(bool start_state) : state(start_state) { }
    virtual ~Toggle() {  }
    bool value() {
        return(state);
    }
    virtual Toggle& activate() {
        state = !state;
        return(*this);
    }
    bool state;
};

La parte crítica resulta ser el state = !state; . Considere lo que sucede cuando cambiamos el código para codificar el estado como int en lugar de bool :

class Toggle {
    enum names{ bfalse = -1, btrue = 1};
    const static names values[2];
    int state;

public:
    Toggle(bool start_state) : state(values[start_state]) 
    { }
    virtual ~Toggle() {  }
    bool value() {  return state==btrue;    }

    virtual Toggle& activate() {
        state = -state;
        return(*this);
    }
};

Este cambio menor mejora la velocidad general en aproximadamente un margen de 5: 1 . A pesar de que el punto de referencia fue destinado para medir el tiempo de llamada del método, en realidad la mayor parte de lo que estaba midiendo era el tiempo para convertir entre int y bool . Ciertamente, estoy de acuerdo en que la ineficiencia mostrada por el original es desafortunada, pero dada la poca frecuencia con que parece surgir en el código real y la facilidad con la que puede solucionarse cuando surja, tengo dificultades para pensar. de lo que significa mucho.

En caso de que alguien decida volver a ejecutar los puntos de referencia involucrados, también debo agregar que hay una modificación casi igual de trivial en la versión de Java que produce (o al menos una vez que se produjo, no he vuelto a ejecutar el pruebas con una JVM reciente para confirmar que todavía lo hacen) una mejora bastante sustancial en la versión de Java también. La versión de Java tiene un NthToggle :: enable () que se ve así:

public Toggle activate() {
this.counter += 1;
if (this.counter >= this.count_max) {
    this.state = !this.state;
    this.counter = 0;
}
return(this);
}

Al cambiar esto para llamar a la función base en lugar de manipular this.state directamente, se obtiene una mejora sustancial de la velocidad (aunque no lo suficiente como para mantenerse al día con la versión modificada de C ++).

Entonces, lo que terminamos es una suposición falsa acerca de los códigos de bytes interpretados frente a algunos de los peores puntos de referencia (que he visto). Tampoco está dando un resultado significativo.

Mi propia experiencia es que con programadores igualmente experimentados que prestan la misma atención a la optimización, C ++ vencerá a Java más a menudo que no, pero (al menos entre estos dos), el lenguaje rara vez hará tanta diferencia como los programadores y el diseño. . Los puntos de referencia que se citan nos dicen más sobre la (in) competencia / (des) honestidad de sus autores que sobre los idiomas que pretenden establecer como puntos de referencia.

[Editar: Como lo implícito en un lugar arriba pero nunca lo dije tan directamente como debería haberlo hecho, los resultados que cito son los que obtuve cuando probé esto hace ~ 5 años, usando las implementaciones de C ++ y Java que eran actuales En ese tiempo. No he vuelto a ejecutar las pruebas con las implementaciones actuales. Sin embargo, una mirada indica que el código no se ha corregido, por lo que todo lo que habría cambiado sería la capacidad del compilador para encubrir los problemas en el código.]

Si ignoramos los ejemplos de Java, sin embargo, es realmente posible para que el código interpretado se ejecute más rápido que el código compilado (aunque es difícil y un tanto inusual).

La forma habitual en que esto sucede es que el código que se interpreta es mucho más compacto que el código de la máquina, o se ejecuta en una CPU que tiene un caché de datos más grande que el del caché de código.

En tal caso, un pequeño intérprete (por ejemplo, el intérprete interno de una implementación de Forth) puede encajar completamente en el caché de código, y el programa que interpreta se ajusta completamente en el caché de datos. La memoria caché suele ser más rápida que la memoria principal en un factor de al menos 10, y con frecuencia mucho más (un factor de 100 ya no es particularmente raro).

Entonces, si el caché es más rápido que la memoria principal por un factor de N, y se necesitan menos de N instrucciones de código de máquina para implementar cada código de byte, el código de byte debería ganar (estoy simplificando, pero creo que el general La idea aún debe ser aparente).

    
respondido por el Jerry Coffin 26.09.2011 - 07:53
109

C / C ++ laminado a mano realizado por un experto con tiempo ilimitado será al menos tan rápido o más rápido que Java. En última instancia, Java en sí está escrito en C / C ++, por lo que, por supuesto, puede hacer todo lo que hace Java si está dispuesto a poner suficiente esfuerzo de ingeniería.

Sin embargo, en la práctica, Java a menudo se ejecuta muy rápido por los siguientes motivos:

  • Compilación JIT : aunque las clases Java se almacenan como un código de bytes, esto suele compilarse en código nativo mediante el compilador JIT a medida que se inicia el programa. Una vez compilado, es un código nativo puro, por lo que teóricamente se puede esperar que funcione tan bien como C / C ++ compilado una vez que el programa se haya ejecutado durante el tiempo suficiente (es decir, después de que se haya realizado toda la compilación JIT)
  • Recolección de basura en Java es extremadamente rápida y eficiente: el Hotspot GC es probablemente la mejor implementación de GC global en el mundo. Es el resultado de muchos años de esfuerzo experto de Sun y otras compañías. Casi cualquier sistema de gestión de memoria complejo que se enrolle en C / C ++ será peor. Por supuesto, puede escribir esquemas de administración de memoria básica bastante rápidos / livianos en C / C ++, pero no serán tan versátiles como un sistema GC completo. Dado que la mayoría de los sistemas modernos necesitan una administración de memoria compleja, Java tiene una gran ventaja para situaciones reales.
  • Mejor segmentación de plataforma : al demorar la compilación al inicio de la aplicación (compilación JIT, etc.), el compilador Java puede aprovechar el hecho de que conoce el procesador exacto que está ejecutando. en. Esto puede habilitar algunas optimizaciones muy beneficiosas que no podría realizar en el código C / C ++ precompilado que necesita apuntar a un conjunto de instrucciones del procesador del "denominador común más bajo".
  • Estadísticas de tiempo de ejecución : debido a que la compilación JIT se realiza en tiempo de ejecución, puede recopilar estadísticas mientras el programa se está ejecutando, lo que permite mejores optimizaciones (por ejemplo, conocer la probabilidad de que se tome una rama en particular). Esto puede permitir que los compiladores JIT de Java produzcan mejor código que los compiladores C / C ++ (que tienen que "adivinar" la rama más probable de antemano, una suposición que a menudo puede ser incorrecta).
  • Muy buenas bibliotecas : el tiempo de ejecución de Java contiene una gran cantidad de bibliotecas muy bien escritas con buen rendimiento (especialmente para aplicaciones del lado del servidor). A menudo, estos son mejores de lo que podría escribir usted mismo o obtener fácilmente para C / C ++.

Al mismo tiempo, C / C ++ también tiene algunas ventajas:

  • Más tiempo para realizar optimizaciones avanzadas : la compilación de C / C ++ se realiza una vez y, por lo tanto, puede dedicar un tiempo considerable a realizar optimizaciones avanzadas si la configura para hacerlo. No hay ninguna razón teórica por la que Java no pueda hacer lo mismo, pero en la práctica desea que Java compile código JIT con relativa rapidez, por lo que el compilador JIT tiende a centrarse en optimizaciones "más simples".
  • Instrucciones que no se pueden expresar en el código de bytes - mientras que el código de bytes de Java es completamente de propósito general, todavía hay algunas cosas que puede hacer en un nivel bajo que no puede hacer en el código de bytes (la aritmética de punteros no verificada es una ¡buen ejemplo!). Al (ab) usar este tipo de trucos, puede obtener algunas ventajas de rendimiento
  • Menos restricciones de "seguridad" : Java realiza un trabajo adicional para garantizar que los programas sean seguros y confiables. Algunos ejemplos son los controles de límites en arreglos, ciertas garantías de concurrencia, controles de puntero nulo, seguridad de tipos, etc. Al evitar estos en C / C ++, puede obtener algunas mejoras de rendimiento (aunque podría decirse que esto puede ser una mala idea).

En general:

  • Java y C / C ++ pueden alcanzar velocidades similares
  • C / C ++ probablemente tenga una ligera ventaja en circunstancias extremas (no es sorprendente que los desarrolladores de juegos AAA aún lo prefieran, por ejemplo)
  • En la práctica, dependerá de cómo se equilibren los diferentes factores enumerados anteriormente para su aplicación en particular.
respondido por el mikera 26.09.2011 - 08:40
19

El tiempo de ejecución de Java isnt interpreta el bytecode. Más bien, utiliza lo que se llama Compilación justo a tiempo . Básicamente, a medida que se ejecuta el programa, toma el código de bytes y lo convierte en código nativo optimizado para la CPU en particular.

    
respondido por el GrandmasterB 26.09.2011 - 06:58
18

En igualdad de condiciones, podría decir: no, Java nunca debería ser más rápido . Siempre se puede implementar Java en C ++ desde cero y, por lo tanto, obtener un rendimiento al menos tan bueno. En la práctica, sin embargo:

  • JIT compila el código en la máquina del usuario final, lo que le permite optimizar para la CPU exacta que están ejecutando. Si bien hay una sobrecarga aquí para la compilación, puede que valga la pena para aplicaciones intensivas. A menudo, los programas de la vida real no se compilan para la CPU que está utilizando.
  • El compilador de Java puede ser mejor optimizando automáticamente las cosas que un compilador de C ++. O puede que no, pero en el mundo real, las cosas no siempre son perfectas.
  • El comportamiento del rendimiento puede variar debido a otros factores, como la recolección de basura. En C ++, normalmente llama al destructor inmediatamente cuando termina con un objeto. En Java, simplemente libera la referencia, retrasando la destrucción real. Este es otro ejemplo de una diferencia que no está ni aquí ni allá, en términos de rendimiento. Por supuesto, puede argumentar que podría implementar GC en C ++ y terminar con esto, pero la realidad es que pocas personas quieren / quieren / pueden.

Como nota aparte, esto me recuerda el debate sobre C en los años 80/90. Todos se preguntaban "¿Puede C ser tan rápido como el montaje?". Básicamente, la respuesta fue: no en papel, pero en realidad el compilador de C creó un código más eficiente que el 90% de los programadores de ensamblados (bueno, una vez que maduró un poco).

    
respondido por el Daniel B 26.09.2011 - 07:23
10
  

Pero la asignación es solo la mitad de la administración de memoria; la desasignación es   la otra mitad. Resulta que para la mayoría de los objetos, la basura directa   El costo de recolección es - cero. Esto se debe a que un coleccionista de copias hace   No es necesario visitar o copiar objetos muertos, solo los vivos. Asi objetos   que se convierten en basura poco después de la asignación no contribuyen a la carga de trabajo   el ciclo de recogida.

     

...

     

Las JVM son sorprendentemente buenas para descubrir cosas que solíamos hacer   Supongamos que solo el desarrollador podría saberlo. Al dejar que la JVM elija   entre la asignación de pila y la asignación de montón en una base de caso por caso,   Podemos obtener los beneficios de rendimiento de la asignación de pila sin hacer   el programador agoniza sobre si asignar en la pila o en la   montón.

enlace

    
respondido por el Landei 26.09.2011 - 08:34
5

Mientras que un programa Java completamente optimizado rara vez vencerá a un programa C ++ completamente optimizado, las diferencias en cosas como la gestión de la memoria pueden hacer que muchos algoritmos se implementen idiomáticamente en Java más rápido que los mismos algoritmos implementados idiomáticamente en C ++.

Como lo señaló @Jerry Coffin, hay muchos casos en los que simples cambios pueden hacer que el código sea mucho más rápido, pero a menudo puede tomar demasiados ajustes impuros en un idioma u otro para que valga la pena mejorar el rendimiento. Eso es probablemente lo que verías en un buen punto de referencia que muestra que Java está mejor que C ++.

Además, aunque por lo general no es tan significativo, hay algunas optimizaciones de rendimiento que un lenguaje JIT como Java puede hacer que C ++ no pueda. El tiempo de ejecución de Java puede incluir mejoras después del código compilado, lo que significa que el JIT puede potencialmente generar código optimizado para aprovechar las nuevas características de la CPU (o al menos diferentes). Por esta razón, un binario de Java de 10 años podría superar a un binario de C ++ de 10 años.

Por último, la seguridad de tipo completa en la imagen más grande puede, en casos muy raros, ofrecer mejoras extremas de rendimiento. Singularity , un sistema operativo experimental escrito casi en su totalidad en un lenguaje basado en C #, tiene una comunicación entre procesos mucho más rápida y realizar tareas múltiples debido al hecho de que no hay necesidad de límites de procesos de hardware o costosos cambios de contexto.

    
respondido por el Rei Miyasaka 26.09.2011 - 12:05
5

Publicado por Tim Holloway en JavaRanch:

  

Este es un ejemplo primitivo: atrás cuando las máquinas funcionaban en   ciclos determinados matemáticamente, una instrucción de rama típicamente tenía 2   diferentes tiempos. Una para cuando se tomó la rama, otra para cuando   rama no fue tomada. Por lo general, el caso de no-rama fue más rápido.   Obviamente, esto significaba que podía optimizar la lógica basada en el   El conocimiento de qué caso era más común (sujeto a la restricción   que lo que "sabemos" no es siempre lo que realmente es el caso).

     

La recompilación JIT lleva esto un paso más allá. Monitorea lo real   uso en tiempo real, y cambia la lógica en función de lo que realmente es el   caso más común Y dale la vuelta de nuevo si la carga de trabajo cambia.   El código compilado estáticamente no puede hacer esto. Así es como Java puede a veces   superan el ensamblado a mano / código C / C ++.

Fuente: enlace

    
respondido por el Thiago Negri 26.09.2011 - 19:31
4

Esto se debe a que el último paso para generar el código de la máquina pasa de forma transparente dentro de la JVM al ejecutar su programa Java, en lugar de hacerlo explícitamente al compilar su proram C ++.

Debería considerar el hecho de que las JVM modernas dedican bastante tiempo a compilar el código de byte sobre la marcha al código de máquina nativo para hacerlo lo más rápido posible. Esto le permite a la JVM hacer todo tipo de trucos de compilación que pueden ser incluso mejores conociendo los datos de perfil del programa que se está ejecutando.

Una cosa tal como alinear automáticamente a un captador, de modo que no se necesita un JUMP-RETURN para obtener un valor, acelera las cosas.

Sin embargo, lo que realmente ha permitido programas rápidos es una mejor limpieza después. El mecanismo de recolección de basura en Java es más rápido que el manual sin malloc en C. Muchas implementaciones modernas sin malloc utilizan un recolector de basura debajo.

    
respondido por el user1249 26.09.2011 - 08:10
4

Respuesta corta - no lo es. Olvídalo, el tema es tan antiguo como el fuego o la rueda. Java o .NET no es ni será más rápido que C / C ++. Es lo suficientemente rápido para la mayoría de las tareas en las que no necesita pensar en la optimización. Al igual que los formularios y el procesamiento de SQL, pero ahí es donde termina.

Para los puntos de referencia, o aplicaciones pequeñas escritas por desarrolladores incompetentes, sí, el resultado final será que Java / .NET probablemente estará cerca y quizás incluso más rápido.

En realidad, las cosas simples como asignar memoria en la pila, o simplemente usar memzones simplemente matarán el Java / .NET en el momento.

El mundo recolectado de basura está usando una especie de zona de memoria con toda la contabilidad. Agregar memzone a C y C será más rápido allí mismo en el lugar. Especialmente para aquellos puntos de referencia de "código de alto rendimiento" de Java contra C, que son los siguientes:

for(...)
{
alloc_memory//Allocating heap in a loop is verrry good, in't it?
zero_memory//Extra zeroing, we really need it in our performance code
do_stuff//something like memory[i]++
realloc//This is lovely speedup
strlen//loop through all memory, because storing string length is soo getting old
free//Java will do that outside out timing loop, but oh well, we're comparing apples to oranges here
}//loop 100000 times

Trate de usar variables basadas en pila en C / C ++ (o ubicación nueva), se traducen en sub esp, 0xff , es una única instrucción x86, supere eso con Java, no puede ...

La mayoría de las veces veo esos bancos en los que se comparan Java con C ++, esto me hace decir, ¿qué? Estrategias erróneas de asignación de memoria, contenedores auto-crecientes sin reservas, múltiples nuevos. Esto ni siquiera está cerca del código C / C ++ orientado al rendimiento.

También es una buena lectura: enlace

    
respondido por el Coder 26.09.2011 - 15:02
2

La realidad es que ambos son simplemente ensambladores de alto nivel que hacen exactamente lo que el programador les dice, exactamente cómo el programador les dice en el orden exacto que el programador les dice. Las diferencias de rendimiento son tan pequeñas que no son intrascendentes para todos los propósitos prácticos.

El lenguaje no es "lento", el programador escribió un programa lento. Muy rara vez un programa escrito de la mejor manera en un idioma supera (para cualquier propósito práctico) un programa que hace lo mismo utilizando la mejor manera del idioma alternativo, a menos que el autor del estudio esté dispuesto a moler su hacha en particular.

Obviamente, si va a un caso poco común como los sistemas incrustados en tiempo real, la elección del idioma puede marcar la diferencia, pero ¿con qué frecuencia es así? y de esos casos, ¿con qué frecuencia la elección correcta no es obvia a ciegas?

    
respondido por el mattnz 26.09.2011 - 09:38
2
  

Vea los siguientes enlaces ... ¿Pero cómo es esto posible? Boggles   mi mente que interpretó el código de bytes podría ser más rápido que un compilado   idioma.

  1. ¿Esas publicaciones de blog proporcionan evidencia confiable?
  2. ¿Las publicaciones del blog proporcionan evidencia definitiva?
  3. ¿Esas publicaciones de blog proporcionan evidencia sobre el "código de bytes interpretado"?

Keith Lea te dice que hay "fallas obvias" pero no hace nada con esas "fallas obvias". En 2005, esas tareas antiguas fueron descartadas y reemplazadas por las tareas ahora mostradas en el juego de puntos de referencia .

Keith Lea le dice que "tomó el código de referencia para C ++ y Java del Gran Desafío del Lenguaje Informático ahora obsoleto y realizó las pruebas" pero en realidad él solo muestra las mediciones de 14 de 25 de esas pruebas obsoletas .

Keith Lea ahora te dice que no estaba tratando de probar nada con la publicación del blog siete años antes, pero en ese entonces dijo: "Estaba harto de escuchar que la gente dice que Java era lento, cuando sé que es bastante rápido ... "Lo que sugiere que en ese entonces había algo que él estaba tratando de probar.

Christian Felde te dice "No creé el código, simplemente volví a ejecutar las pruebas". como si eso lo absolviera de cualquier responsabilidad por su decisión de publicar las mediciones de las tareas y los programas que Keith Lea seleccionó.

¿Las mediciones de hasta 25 pequeños programas proporcionan evidencia definitiva?

Esas mediciones son para programas ejecutados como "modo mixto" Java no interpretado Java - "Recuerda cómo funciona HotSpot . " Puede descubrir fácilmente qué tan bien se ejecuta Java" bytecode interpretado ", porque puede forzar a Java a solo interpretar el bytecode - simplemente cronometre algunos programas Java ejecutados con y sin la opción -Xint .

    
respondido por el igouy 26.09.2011 - 19:47
-1

Me divierte lo generalizada que es esta extraña noción de "código de bytes interpretado". ¿Alguna vez han escuchado acerca de la compilación JIT? Tu argumento no se puede aplicar a Java.

Pero, dejando a un lado la JVM, hay casos en que un código de subproceso directo o incluso una interpretación trivial de bytecode puede superar fácilmente a un código nativo altamente optimizado. La explicación es bastante simple: el código de bytes puede ser bastante compacto y se ajustará a su pequeña memoria caché cuando una versión de código nativo del mismo algoritmo terminará teniendo varias fallas de memoria caché para una sola iteración.

    
respondido por el SK-logic 26.09.2011 - 08:25
-1

Aparte de JIT, GC y demás, C ++ puede ser muy, muy fácil de hacer mucho más lento que Java. Esto no se mostrará en los puntos de referencia, pero la misma aplicación escrita por el desarrollador de Java y un desarrollador de C ++ puede ser mucho más rápida en Java.

  • Sobrecarga del operador. Cada operador simple como "+" o "=" puede llamar a cientos de líneas de código haciendo comprobaciones de seguridad, operaciones de disco, registro, seguimiento y creación de perfiles. Y son tan fáciles de usar que una vez que sobrecargas a los operadores, los usas de forma natural y copiosa sin darte cuenta de cómo se acumula el uso.
  • Plantillas. Estos no afectan tanto la velocidad como la memoria. El uso no cauteloso de las plantillas conducirá a la generación de millones de líneas de código (alternativas para la plantilla básica) sin que te des cuenta de ellas. Pero luego los tiempos de carga binarios, el uso de memoria, el uso de intercambio, todo eso actúa también contra los puntos de referencia. Y el uso de la memoria RAM va por las nubes.

En cuanto a los patrones de herencia avanzados, estos son bastante similares: C ++ tiene algunos que Java no, y viceversa, pero todos ellos también presentan una sobrecarga similar y significativa. Así que no hay una ventaja especial de C ++ en la programación de objetos pesados.

Una advertencia más: GC puede ser más rápido o más lento que administrar las asignaciones manualmente. Si asigna una gran cantidad de objetos pequeños, en el entorno de GC, por lo general, se asigna una parte de la memoria y partes de ella se envían según sea necesario para los nuevos objetos. En administrado - cada objeto = asignación separada toma un tiempo significativo. OTOH, si malloc () mucha memoria a la vez y luego asigna partes de ella a sus objetos manualmente, o usa pocas instancias más grandes de objetos, puede subir mucho más rápido.

    
respondido por el SF. 26.09.2011 - 09:07
-2

De alguna manera, Stack Exchange no toma mis otros puntos de pila así que ... no hay respuesta desafortunadamente ...

Sin embargo, la segunda respuesta más votada aquí está llena de desinformación en mi humilde opinión.

Una aplicación enrollada a mano por un experto en C / C ++ SIEMPRE va a ser mucho más rápida que una aplicación Java, punto. No hay 'tan rápido como Java o más rápido'. es más rápido, precisamente por los elementos que cita a continuación:

Compilación JIT : ¿Realmente espera que un optimizador automático tenga la inteligencia de un programador experto y vea el vínculo entre la intención y el código que la CPU realmente va a ejecutar? Además, todo el JIT que haces es el tiempo perdido comparado con un programa ya compilado.

Recolección de basura es una herramienta que simplemente desasigna recursos que un programador habría olvidado asignar, de una manera más o menos eficiente.

Evidentemente, esto solo puede ser más lento de lo que haría un programador experto de C (que escogiste el término) para manejar su memoria (y no hay fugas en las aplicaciones escritas correctamente).

Una aplicación C con rendimiento optimizado sabe en qué CPU se está ejecutando, se ha compilado en ella, de lo contrario, significa que no has tomado todos los pasos para el rendimiento, ¿verdad?

Estadísticas de tiempo de ejecución Esto está más allá de mi conocimiento, pero sospecho que un experto en C tiene conocimientos de predicción de sucursales más que suficientes para ser más astuto que la optimización automatizada -

Muy buenas bibliotecas Hay muchas funciones no muy optimizadas disponibles a través de las bibliotecas en Java, y lo mismo ocurre en cualquier idioma, sin embargo, las bibliotecas más optimizadas están escritas en C, especialmente para cálculo.

La JVM es una capa de abstracción, que implica ambas cosas buenas, muchas de las cuales están arriba, y también implica que la solución general es más lenta por el diseño.

En general:

Java nunca puede alcanzar la velocidad de C / C ++ debido a la forma en que funciona en una JVM con mucha protección, características y herramientas.

C ++ tiene una clara ventaja clara en el software optimizado, ya sea para computación o juegos, y es común ver a las implementaciones de C ++ ganar concursos de codificación hasta el punto de que las mejores implementaciones de Java solo pueden verse en la segunda página.

En la práctica, C ++ no es un juguete y no le permitirá resolver muchos errores que la mayoría de los lenguajes modernos pueden manejar, sin embargo, al ser más simple y menos seguro, es inherentemente más rápido.

Y como conclusión, me gustaría decir que la mayoría de las personas no dan dos centavos por esto, que al final la optimización es un deporte reservado solo a unos pocos desarrolladores afortunados y eso, excepto en los casos en que el rendimiento realmente es una preocupación (es decir, cuando la multiplicación de hardware por 10 no lo ayudará, o representará unos pocos millones al menos), la mayoría de los administradores preferirán una aplicación no optimizada y una tonelada de hardware.

    
respondido por el Morg. 26.09.2011 - 18:15
-4

He visto al menos dos mmo impresionantes hechos en Java, decir que no es lo suficientemente rápido para los juegos es un nombre inapropiado. El hecho de que los diseñadores de juegos prefieren C ++ más que otros lenguajes dice que simplemente no está relacionado con Java, simplemente significa que los programadores nunca han incursionado en ningún otro lenguaje o paradigma de programación. Cualquier cosa en cualquier lenguaje tan avanzado como C / C ++ o incluso Java puede producir código que técnicamente podría cumplir o anular el argumento de la velocidad. Todo lo que se dice bien y todo se reduce a lo que los programadores saben, con qué equipos trabajan más y, lo que es más importante, por qué usan dichas herramientas. Ya que estamos abordando el aspecto de desarrollo del juego de la programación, entonces debe haber más en el argumento. En pocas palabras, se trata de dinero y tiempo para una empresa que no tiene nada que ver con el uso de herramientas que cumplan con el control de calidad y, en el mundo real, no influye en las razones de xx para elegir C ++ en lugar de Java o cualquier otro idioma. Es solo una decisión de producción en masa. En el nivel más básico de algoritmos de computación, todos con los que jugamos son unos y ceros, el argumento de la velocidad es uno de los argumentos más tontos jamás aplicados a los juegos. Si desea que la velocidad aumente tanto, elimine por completo los lenguajes de programación y trabaje con el ensamblaje, que es la mejor ventaja con diferencia.

    
respondido por el Meh 06.06.2015 - 13:41

Lea otras preguntas en las etiquetas