CountDownLanth (counter) + CyclicBarrier (loop fence) + Semaphore (semaphore)

CountDownLatch usage

 CountDownLatch class java.util.concurrent located under the package, which may be implemented using functionally similar counter. For example, there is a task A, it waits for other duties to perform after completion, then you can use this function to achieve the CountDownLatch. (Mainline Chengkai Qi child thread running when the child thread is not over when the main thread can wait until the ready counter count is initialized to 0, the main thread can continue execution without waiting for a)

  1. public CountDownLatch(int count) {  };//构造方法,参数count为计数值
  2. public void await() throws InterruptedException { };//调用此方法线程会被挂起,它会等待直到count值为0才继续执行
  3. public boolean await(long timeout, TimeUnit unit) throws InterruptedException { };//和await()类似,只不过等待一定的时间后count值还没变为0的话就会继续执行
  4. public void countDown() { };//将count值减1
package JUC;

import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
import java.util.stream.IntStream;

/**
 * @author Heian
 * @time 19/04/01 23:28
 */
public class CountDownLanthDemo {
    static class Test implements Runnable{
        private CountDownLatch countDownLatch;
        public Test(CountDownLatch countDownLatch) {
            this.countDownLatch = countDownLatch;
        }
        //子线程的工作
        @Override
        public void run() {
            try {
                System.out.println("子线程开始工作,子线程为:"+ Thread.currentThread ().getName ());
                TimeUnit.SECONDS.sleep (3);
            } catch (InterruptedException e) {
                e.printStackTrace ();
            }finally {
                System.out.println ("countDownLatch大小" + countDownLatch.getCount ());//这里会出现数据不一致情况,并行访问同一个资源导致
                countDownLatch.countDown ();//执行完线程数量-1
            }
        }
    }
    private static void doLastWork(){
        System.out.println ("你做完了工作,该轮到我了");
    }

    public static void main(String[] args) throws InterruptedException{
        CountDownLatch countDownLatch = new CountDownLatch (5);//定义5个子线程
        IntStream.range (0,5).forEach (value -> {
            new Thread (new Test(countDownLatch)).start ();
        });
        countDownLatch.await ();//阻塞main线程,需要等到自定义线程执行完成后方能执行
        doLastWork();
    }
}

CyclicBarrier usage

回环栅栏:让一组线程等待至某个状态之后再全部同时执行。
叫做回环是因为当所有等待线程都被释放以后,CyclicBarrier可以被重用。
叫做栅栏,大概是描述所有线程被栅栏挡住了,当都达到时,一起跳过栅栏执行,也算形象。我们可以把这个状态就叫做barrier。
 

  1. public CyclicBarrier (int parties); // parameter parties refers to how many threads to make or tasks waiting to barrier state
  2. public CyclicBarrier (int parties, Runnable barrierAction); // parameter barrierAction content when these threads have reached the barrier state will perform.
  3. public int await() throws InterruptedException, BrokenBarrierException { };//To suspend the current thread, until all threads have reached the barrier state again while performing subsequent tasks;
  4. public int await(long timeout, TimeUnit unit)throws InterruptedException,BrokenBarrierException,TimeoutException { };//These threads wait until a certain time, if there is no thread to reach the barrier state to directly thread reaches the barrier of the rest.
package JUC;

import java.util.concurrent.CyclicBarrier;
import java.util.stream.IntStream;

/**
 * @author Heian
 * @time 19/04/03 16:32
 */

public class CyclicBarrierDemo {

    static class runtask implements Runnable{
        private CyclicBarrier cyclicBarrier;
        public runtask(CyclicBarrier cyclicBarrier) {
            this.cyclicBarrier = cyclicBarrier;
        }
        @Override
        public void run() {
            try {
                System.out.println (Thread.currentThread ().getName () +  "准备睡眠");
                cyclicBarrier.await ();
                Thread.sleep (5000);
                System.out.println (Thread.currentThread ().getName () + "开始跳出栅栏");
            } catch (Exception e) {
                e.printStackTrace ();
            }
        }
    }

    public static void main(String[] args) throws Exception{
        //这里可以模拟junit并发测试  一次性发1000个请求,只有当请求数量达到了,才跳出栅栏出发
        CyclicBarrier cyclicBarrier = new CyclicBarrier (3);
        IntStream.range (0,3).forEach (value -> {//当线程不足时,不会触发跳出栅栏动作
            new Thread (new runtask(cyclicBarrier)).start ();
        });

    }


}

Semaphore Usage

Semaphore literally Semaphore, Semaphore can control the number of threads simultaneously access, obtain a license by acquire (), if not wait, and release () Releases a permit.

Construction method

  1. public Semaphore ( int Permits) {}   // Permits parameter represents the number of licenses, i.e., while the number of threads may be allowed access
  2. public Semaphore ( int Permits, boolean fair) {}    // this one more parameter indicates whether the fair is fair, that is, the longer the wait, the more first obtain permission

The following four methods commonly used are blocked

  1. void public Acquire () throws InterruptedException {}     // get a license if no license can be obtained, it will have to wait until a license
  2. void public Acquire ( int Permits) throws InterruptedException {}     // Get Permits licenses
  3. void public Release () {}          // release a license note before releasing the license, you must obtain permission.
  4. void public Release ( int Permits) {}     // release Permits licenses

If you want to immediately get the results, you can use the following several methods

  1. Boolean public to tryAcquire () {};    // try to obtain a license, if the acquisition is successful, immediately returns true, if the acquisition has failed, then immediately returns false
  2. boolean public tryAcquire ( Long timeout, TimeUnit Unit) throws InterruptedException {};  // try to obtain a license, if succeed within the specified time, then immediately return true, otherwise it returns false immediately
  3. Boolean public to tryAcquire ( int Permits) {}; // try to obtain Permits licenses, if the acquisition is successful, immediately returns true, if the acquisition has failed, then immediately returns false
  4. boolean public tryAcquire ( int permits, Long timeout, TimeUnit Unit) throws InterruptedException {}; // try to obtain permits licenses, if succeed within the specified time, then immediately return true, otherwise it returns false immediately
  5. NOTE: Also () method to obtain the number of available licenses by availablePermits.

If a plant has five machines, but there are eight workers, while a machine can only be used by a worker, just ran out, the other workers to continue. Then we can be done by Semaphore:

package JUC;

import java.util.concurrent.Semaphore;
import java.util.stream.IntStream;

/**
 * @author Heian
 * @time 19/04/03 21:36
/
public class SemaphoreDemo {

    static class worker implements Runnable{
        private int workerNo;
        private Semaphore semaphore;
        public worker(int workerNo, Semaphore semaphore) {
            this.workerNo = workerNo;
            this.semaphore = semaphore;
        }
        @Override
        public void run() {
            try {
                semaphore.acquire ();//没有的话就会处于阻塞
                System.out.println (this.workerNo +  "员工号获得机器上生产的许可");
                Thread.sleep (5000);
                semaphore.release ();
                System.out.println (this.workerNo + "员工号释放机器");
            } catch (InterruptedException e) {
                e.printStackTrace ();
            }
        }
    }

    public static void main(String[] args) {
        int permits = 5;//许可数  机器数目
        Semaphore semaphore = new Semaphore (permits);
        int workefs = 8;
        IntStream.range (0,workefs).forEach (value -> {
            new Thread (new worker(value,semaphore)).start ();
        });
    }
}

0 employee number to release the machine
1 employees No. releasing machine
2 employee ID release machine
7 employee number to productive machine license
6 employee number to productive machine licenses
3 employee number released machine
5 employee number obtained production machine license
4 employee number release the machine
5 machine release No. of employees
7 employees release machine No.
6 staff numbers released machine

Three auxiliary class Summary:

(1) CountDownLatch and are able to achieve CyclicBarrier wait between threads, but they have different emphases: After CountDownLatch A generally used for a thread to wait several other threads executing the task, it was executed; and for a general CyclicBarrier group of threads waiting for each other to a certain state, then this group of threads again performed simultaneously; in addition, CountDownLatch not be able to reuse, and CyclicBarrier can be reused.

(2) Semaphore is actually somewhat similar and lock, it is generally used to control access to a resource group, the above example is the number of locks were controlled.

Reference from: http://www.importnew.com/21889.html

 

Guess you like

Origin blog.csdn.net/qq_40826106/article/details/89003634