Pregunta

Archivo: Ejemplo1.java

public class Example1 implements Runnable {

    public void run() {
        for(int i = 0; i < 100000000; i++) {
            int x = 5;
            x = x * 4;
            x = x % 3;
            x = x + 9000;
            x = x * 923;
        }
    }

    public static void task() {
        for(int i = 0; i < 100000000; i++) {
            int x = 5;
            x = x * 4;
            x = x % 3;
            x = x + 9000;
            x = x * 923;
        }
        for(int i = 0; i < 100000000; i++) {
            int x = 9;
            x = x * 2;
            x = x % 4;
            x = x + 3241;
            x = x * 472;
        }
    }

    public static void main(String[] args) {

        long startTime = System.currentTimeMillis();
            Example1.task();
            Example1.task();
            Example1.task();
            Example1.task();
            Example1.task();
        long stopTime = System.currentTimeMillis();
        long runTime = stopTime - startTime;
        System.out.println("Run time for one thread: " + runTime);


        startTime = System.Example1();
            (new Thread(new Example1())).start();
            (new Thread(new Example2())).start();
            (new Thread(new Example1())).start();
            (new Thread(new Example2())).start();
            (new Thread(new Example1())).start();
            (new Thread(new Example2())).start();
            (new Thread(new Example1())).start();
            (new Thread(new Example2())).start();
            (new Thread(new Example1())).start();
            (new Thread(new Example2())).start();
        stopTime = System.currentTimeMillis();
        runTime = stopTime - startTime;
        System.out.println("Run time for two threads: " + runTime);


    }

}

Archivo: Example2.java

public class Example2 implements Runnable {

    public void run() {
        for(int i = 0; i < 100000000; i++) {
            int x = 9;
            x = x * 2;
            x = x % 4;
            x = x + 3241;
            x = x * 472;
        }        
    }
}

Cuando ejecuto esto, genera:

  

Tiempo de ejecución para un hilo: 1219

     

Tiempo de ejecución para dos hilos: 281

o algo muy cercano.

¿Por qué hay tanta diferencia? ¿Por qué dividirlo en dos hilos va más de dos veces más rápido que simplemente ejecutarlo directamente?

¿Fue útil?

Solución

En realidad no estás esperando que los hilos terminen en absoluto.

Una vez que inicia un hilo, debe llamar a .join () para esperar a que se complete. Lo que está sucediendo aquí es que todos sus hilos están comenzando y tan pronto como el último ha comenzado, usted lo registra y luego calcula el tiempo de parada. Esto significa que sus hilos todavía se están ejecutando en segundo plano.

Editar: La razón por la que la primera tarda tanto es porque estás haciendo una serie de llamadas sincrónicas, mientras creas un hilo y lo inicias genera una tarea asincrónica.

Edición 2: Aquí hay un diagrama de secuencia de servilletas de lo que sucede en su primera prueba: Qiq / cdraw? lz = TWFpbi0-RXhhbXBsZTE6IFRhc2sgc3RhcnRlZAphY3RpdmF0ZSAAGAgKACEILS0-TWFpbjogZG9uZQpkZQAYEgABWAABWAABgTFlMQo & amp; s

Aquí hay un diagrama de secuencia de servilletas de lo que sucede en su segunda prueba: http://www.websequencediagrams.com/cgi-bin/cdraw?lz = TWFpbi0tPkFub255bW91cyBUaHJlYWQ6IFN0YXJ0IEV4YW1wbGUxLnRhc2soKQoACSYyAAEuAAFdAAGBOwCCPjoAgyIGPk1haW46ICJIb3cgbG9uZyBkaWQgdGhhdCB0YWtlPyIKAINmEC0AKwhUYXNrcyBiZWdpbiB0byBmaW5pc2guLi4gKHNvbWUgbWF5IGhhdmUgZW5kZWQgZWFybGllcikK & amp; s = servilleta

Edición 3: Acabo de darme cuenta de que el segundo diagrama de secuencia apunta todas las flechas al / mismo / hilo. De hecho, son hilos DIFERENTES, cada llamada.

Otros consejos

La llamada start () en un subproceso vuelve inmediatamente porque solo pone en cola el subproceso. El subproceso comenzará a ejecutarse en segundo plano algún tiempo después.

Esto es lo que obtengo con su código agregando unirse a los hilos:

  

Tiempo de ejecución para un hilo: 566

     

Tiempo de ejecución para dos hilos: 294

Entonces las respuestas anteriores son correctas.

EDITAR: agregué uniones de esta manera. Puedes hacerlo mejor, pero no importa:

    Thread[] t = new Thread[10];
    (t[0] = new Thread(new Example1())).start();
    (t[1] = new Thread(new Example2())).start();
    (t[2] = new Thread(new Example1())).start();
    (t[3] = new Thread(new Example2())).start();
    (t[4] = new Thread(new Example1())).start();
    (t[5] = new Thread(new Example2())).start();
    (t[6] = new Thread(new Example1())).start();
    (t[7] = new Thread(new Example2())).start();
    (t[8] = new Thread(new Example1())).start();
    (t[9] = new Thread(new Example2())).start();

    for (Thread t1: t) {
        try {
            t1.join();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

Tienes que unirte a cada hilo. Sin embargo, no pierde el tiempo esperando en join () porque otros hilos no están bloqueados. Si el hilo ha finalizado su ejecución antes de llamar para unirse, simplemente continúe con el siguiente hilo.

Además, ¿qué significa tu último comentario?

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top