Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java并发中倒计时锁实例的实践_Java_Multithreading_Concurrency - Fatal编程技术网

Java并发中倒计时锁实例的实践

Java并发中倒计时锁实例的实践,java,multithreading,concurrency,Java,Multithreading,Concurrency,我正在阅读Java并发性实践手册,遇到了倒计时锁 以下是给出的示例: public class TestHarness { public long timeTasks(int nThreads, final Runnable task) throws InterruptedException { final CountDownLatch startGate = new CountDownLatch(1); final CountDownL

我正在阅读Java并发性实践手册,遇到了倒计时锁

以下是给出的示例:

public class TestHarness {
    public long timeTasks(int nThreads, final Runnable task)
        throws InterruptedException {

        final CountDownLatch startGate = new CountDownLatch(1);
        final CountDownLatch endGate = new CountDownLatch(nThreads);

        for (int i = 0; i < nThreads; i++) {
            Thread t = new Thread() {

                public void run() {
                    try {
                        startGate.await();
                        try {
                            task.run();
                        } finally {
                            endGate.countDown();
                        }
                    } catch (InterruptedException ignored) { }
                }
            };
            t.start();
        }
        long start = System.nanoTime();
        startGate.countDown();
        endGate.await();
        long end = System.nanoTime();
        return end-start;
    }
}

请帮助我理解这个概念。

这段代码

Thread t = new Thread() {

    public void run() {
        try {
            startGate.await();
            try {
                task.run();
            } finally {
                endGate.countDown();
            }
        } catch (InterruptedException ignored) { }
    }
};
设置所需的所有线程。每个线程将等待
startGate
被“打开”,即其计数变为0。当线程执行完
Runnable
,即
run()
返回时,它们将对
endGate
进行倒计时。这就是为什么

每个工作线程所做的第一件事是等待启动门; 这确保了它们在全部准备就绪之前都不会开始工作 开始。每个人做的最后一件事是在终点门上倒计时

意味着

设置所有线程后,将执行此代码

long start = System.nanoTime();
startGate.countDown();
endGate.await();
long end = System.nanoTime();
return end-start;
当前线程倒计时
startGate
,这允许所有其他线程开始执行其
Runnable
,即
task.run()
。然后等待
端门上的(块)倒计时到0。在这一点上,它会计算花费的时间并返回该值。这就是为什么

这允许主线程高效地等待,直到最后一个 工作线程已完成,因此它可以计算经过的时间


意思是

只要不清楚您已经知道了什么,实际上并不完全清楚您的实际问题是什么,或者代码应该如何解释

但是,此处使用的概念并不复杂,通过删除错误处理并用内嵌注释指出重要部分,可能已经变得更加清晰:

for (int i = 0; i < nThreads; i++) {

    // This will create and start a new thread
    // that executes the code in the "run" method
    Thread t = new Thread() {
        public void run() {

            // Wait until this thread gets the start signal
            startGate.await();

            // Perform some arbitrary work
            task.run();

            // Notify everybody that this thread has finished his work
            endGate.countDown();
        }
    };
    t.start(); 
}

// Give all threads the start signal: Counting down
// where will cause the latch to reach the value 0,
// and every thread that is waiting at "startGate.await()"
// will proceed his work
startGate.countDown();

// Wait here until all threads have called "endGate.countDown()".
endGate.await();
for(inti=0;i
开始日期最初设置为1,因此所有线程将等待,直到倒计时

endGate
被初始化为我们计划使用的线程数,因此它将等待所有线程通过endGate,然后报告所用的时间

// Take a note of the time.
long start = System.nanoTime();
// Start all of the threads running - they all wait for this signal by calling startGate.await().
startGate.countDown();
// Wait for all threads to complete - they record their finish with endGate.countDown().
endGate.await();
// Note the time.
long end = System.nanoTime();
package com.sample.thread;
导入java.util.concurrent.CountDownLatch;
公共类CDLExample{
专用静态倒计时锁存器;
公共静态void main(字符串参数[]){
闩锁=新的倒计时闩锁(2);
新线程(“主线程”){
公开募捐{
试一试{
satch.wait();
系统输出
.println(“\n在启动所有其他线程时启动主线程”);
System.out.println(“倒计时锁存器:
+Thread.currentThread().getName());
}捕捉(中断异常e){
e、 printStackTrace();
}
}
}.start();
新线程(“第一个”){
公开募捐{
System.out.println(“打印奇数:”
+Thread.currentThread().getName());
试一试{
对于(int i=1;i<20;i=i+2){
系统输出打印(i+“”);
睡眠(50);
}
}捕捉(中断异常e){
e、 printStackTrace();
}
倒计时();
}
}.start();
新线程(“第二个”){
公开募捐{
试一试{
睡眠(1000);
System.out.println(“\n打印偶数:”
+Thread.currentThread().getName());
对于(int i=2;i<20;i=i+2){
睡眠(50);
系统输出打印(i+“”);
}
}捕捉(中断异常e){
e、 printStackTrace();
}
倒计时();
}
}.start();
}

}

如果您不知道多线程是如何工作的,为什么要从倒数锁存开始呢?放慢速度。开始。@SotiriosDelimanolis,我正在用这本书学习多线程的概念,因为这是so中许多专家的建议。但是我在理解这个例子时遇到了困难。这本书不应该被用作多线程的介绍,因为你可以在本书的“如何使用”一节中清楚地读到。同一部分列出了建议的介绍性来源。启动线程需要时间。因此,如果每个线程一启动就执行它的任务,那么一些线程可能已经在运行,而另一些线程可能还没有创建。所以他们使用锁存器等待,直到主线程发出启动信号。就像在一场真正的赛跑中一样。当他们完成任务时,他们会发出信号,以便主线可以知道所有的马何时都完成了。想象一下赛马,当所有的马都在起跑线上时比赛才开始,直到最后一匹马到达终点线时比赛才结束。
for (int i = 0; i < nThreads; i++) {

    // This will create and start a new thread
    // that executes the code in the "run" method
    Thread t = new Thread() {
        public void run() {

            // Wait until this thread gets the start signal
            startGate.await();

            // Perform some arbitrary work
            task.run();

            // Notify everybody that this thread has finished his work
            endGate.countDown();
        }
    };
    t.start(); 
}

// Give all threads the start signal: Counting down
// where will cause the latch to reach the value 0,
// and every thread that is waiting at "startGate.await()"
// will proceed his work
startGate.countDown();

// Wait here until all threads have called "endGate.countDown()".
endGate.await();
// Take a note of the time.
long start = System.nanoTime();
// Start all of the threads running - they all wait for this signal by calling startGate.await().
startGate.countDown();
// Wait for all threads to complete - they record their finish with endGate.countDown().
endGate.await();
// Note the time.
long end = System.nanoTime();
package com.sample.thread;

import java.util.concurrent.CountDownLatch;

public class CDLExample {

private static CountDownLatch latch;

public static void main(String args[]) {
    latch = new CountDownLatch(2);

    new Thread("main") {
        public void run() {
            try {
                latch.await();
                System.out
                        .println("\nStarting Main thread as all other thread is started");
                System.out.println("CountDownLatch demonstrated: "
                        + Thread.currentThread().getName());
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }

    }.start();

    new Thread("first") {
        public void run() {
            System.out.println("Print Odd Number: "
                    + Thread.currentThread().getName());
            try {
                for (int i = 1; i < 20; i = i + 2) {
                    System.out.print(i + " ");
                    Thread.sleep(50);
                }
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            latch.countDown();
        }
    }.start();

    new Thread("second") {
        public void run() {
            try {
                Thread.sleep(1000);
                System.out.println("\nPrint Even Number: "
                        + Thread.currentThread().getName());

                for (int i = 2; i < 20; i = i + 2) {
                    Thread.sleep(50);
                    System.out.print(i + " ");
                }
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            latch.countDown();
        }
    }.start();
}