有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

多线程为什么两个Java线程(在某些情况下)的速度是一个线程的两倍以上?

文件:示例1。爪哇

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);
        

    }
    
}

文件:示例2。爪哇

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;
        }        
    }
}

当我运行它时,它会输出:

Run time for one thread: 1219

Run time for two threads: 281

或者非常接近的东西

为什么会有这样的差异?为什么把它分成两个线程比直接运行要快两倍多


共 (3) 个答案

  1. # 1 楼答案

    线程上的调用start()会立即返回,因为它只是让线程排队。 线程本身将在一段时间后开始在后台运行

  2. # 2 楼答案

    实际上,您根本不需要等待线程完成

    启动线程后,必须调用。在其上join()以等待其完成。这里发生的事情是,所有线程都在启动,一旦最后一个线程启动,就给它计时,然后计算停止时间。这意味着您的线程仍在后台运行

    编辑:第一个线程花费这么长时间的原因是,您正在进行一系列同步调用,同时创建一个线程并启动它生成一个异步任务

    编辑2:以下是第一次测试中发生的事情的餐巾纸序列图: http://www.websequencediagrams.com/cgi-bin/cdraw?lz=TWFpbi0-RXhhbXBsZTE6IFRhc2sgc3RhcnRlZAphY3RpdmF0ZSAAGAgKACEILS0-TWFpbjogZG9uZQpkZQAYEgABWAABWAABgTFlMQo&s=napkin

    下面是第二次测试的餐巾纸顺序图: http://www.websequencediagrams.com/cgi-bin/cdraw?lz=TWFpbi0tPkFub255bW91cyBUaHJlYWQ6IFN0YXJ0IEV4YW1wbGUxLnRhc2soKQoACSYyAAEuAAFdAAGBOwCCPjoAgyIGPk1haW46ICJIb3cgbG9uZyBkaWQgdGhhdCB0YWtlPyIKAINmEC0AKwhUYXNrcyBiZWdpbiB0byBmaW5pc2guLi4gKHNvbWUgbWF5IGhhdmUgZW5kZWQgZWFybGllcikK&s=napkin

    编辑3:我刚刚意识到第二个序列图将所有箭头指向/same/线程。它们实际上是不同的线程,每次调用

  3. # 3 楼答案

    下面是我通过您的代码向线程添加join得到的结果:

    Run time for one thread: 566

    Run time for two threads: 294

    所以前面的答案是正确的

    编辑:我这样添加了连接。你可以做得更好,但没关系:

        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();
            }
        }
    

    你必须加入每个线程。但是,您不会浪费时间等待join(),因为其他线程不会被阻塞。如果该线程在您调用join之前已经完成了它的执行,那么您只需继续下一个线程

    还有,你最后的评论是什么意思