Java并发和高并发学习总结(四)- J.U.C之工具类

1、总览

  • CountDownLatch允许一个或多个线程等待某些操作完成
  • Semaphore Java版本的信号量实现
  • CyclicBarrier 一种辅助性的同步结构,允许多个线程等待到达某个屏障
  • Exchanger 在线程间交换数据的一种手段

    2、CountDownLatch

    当一个或多个线程需要等待其他线程完成操作时,就可以使用CountDownLatch了,当然,最简单的你也可以使用join方法

    2.1、join

public class JoinTest {
    public static void main(String[] args) throws InterruptedException {
        Thread parser1 = new Thread(new Runnable() {
            @Override
            public void run() {
            }
        });
        Thread parser2 = new Thread(new Runnable() {
            @Override
            public void run() {
                System.out.println("parser2 finish");
            }
        });
        parser1.start();
        parser2.start();
        parser1.join();
        parser2.join();
        System.out.println("all parser finish");
    }
}

join线程用于让当前执行线程等待join线程执行结束,其实现原理是不停检查join线程是否存活,如果join线程存活则让当期线程永远等待。其中wait(0)表示永远等待下去。知道join线程中止后,线程的this.notifyAll()方法会被调用,调用notifyAll()方法是在JVM中实现的。

2.1、CountDownLatch实现

CountDownLatch更为巧妙的实现了这个需求,并且比join的功能更为强大。

public class CountDownLatchTest {
    static CountDownLatch c = new CountDownLatch(2);
    public static void main(String[] args) throws InterruptedException {
        new Thread(new Runnable() {
            @Override
            public void run() {
                System.out.println(1);
                c.countDown();
                System.out.println(2);
                c.countDown();
            }
        }).start();
        c.await();
        System.out.println("3");
    }
}

构造函数接收一个int类型的参数作为计数器,N这里指可能要等待的点。

当调用countDwon方法时,N减一,await方法则会阻塞当前线程,知道N变成0。await方法还有一个带指定时间的重载方法await(long time,TimeUnit unit),等待时间结束后,就不在阻塞当前线程。

关于实现,在前面一篇有提到,这里就不在赘述。

3、CyclicBarrier

字面意思是可循环使用的屏障,他要做的事情是让一组线程到达一个屏障时被阻塞,直到最后一个线程到达屏障时,屏障才会开门,所有被屏障拦截的线程才会继续运行。

3.1、CyclicBarrier的使用

CyclicBarrier要拦截的线程数在构造方法中声明,每个线程调用await方法通知CyclicBarrier已到达屏障,然后当前线程被阻塞。

public class CyclicBarrierTest {

    static CyclicBarrier c = new CyclicBarrier(2);

    public static void main(String[] args){
        new Thread(new Runnable(){
            public void run(){
                try {
                    c.await();
                } catch (Exception e) {
                    e.printStackTrace();
                }
                System.out.println(1);
            }
        }).start();
        try {
            c.await();
        } catch (Exception e){
            e.printStackTrace();
        }
        System.out.println(2);
    }

}

CyclicBarrier还提供一个更高级的构造函数CyclicBarrier(int parties,Runnable barrierAction),用于在线程到达屏障时,优先执行barrierAction,以方便处理更复杂的业务场景。

3.2、CyclicBarrier和CountDownLatch的区别

CountDownLatch的计数器只能使用一次,而CyclicBarrier的计数器可以使用reset()方法重

置。所以CyclicBarrier能处理更为复杂的业务场景。例如,如果计算发生错误,可以重置计数

器,并让线程重新执行一次。

CyclicBarrier还提供其他有用的方法,比如getNumberWaiting方法可以获得Cyclic-Barrier

阻塞的线程数量。isBroken()方法用来了解阻塞的线程是否被中断。

4、semaphore

Semaphore(信号量)是用来控制同时访问特定资源的线程数量,它通过协调各个线程,以保证合理的使用公共资源。

public class SemaphoreTest {

    private static final int THREAD_COUNT = 30;
    private static ExecutorService threadPool =
            Executors.newFixedThreadPool(THREAD_COUNT);
    private static Semaphore s = new Semaphore(10);

    public static void main(String[] args) {
        // TODO Auto-generated method stub
        for(int i=0;i < THREAD_COUNT;i++){
            threadPool.execute(new Runnable(){

                public void run() {
                    // TODO Auto-generated method stub
                    try {
                        s.acquire();
                        System.out.println("sava data!");
                        Thread.sleep(5000);
                        s.release();
                    } catch (InterruptedException e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }

                }

            });
        }
        threadPool.shutdown();
    }

}

在代码中,虽然有30个线程在执行,但是只允许10个并发执行。Semaphore的构造方法

Semaphore(int permits)接受一个整型的数字,表示可用的许可证数量。Semaphore(10)表示允

许10个线程获取许可证,也就是最大并发数是10。Semaphore的用法也很简单,首先线程使用

Semaphore的acquire()方法获取一个许可证,使用完之后调用release()方法归还许可证。

其他方法

  • ·intavailablePermits():返回此信号量中当前可用的许可证数。
  • ·intgetQueueLength():返回正在等待获取许可证的线程数
  • booleanhasQueuedThreads():是否有线程正在等待获取许可证
  • void reducePermits(int reduction):减少reduction个许可证,是个protected方法
  • ·Collection getQueuedThreads():返回所有等待获取许可证的线程集合,是个protected方法

    5、Exchanger

    Exchanger(交换者)是一个用于线程间协作的工具类。Exchanger用于进行线程间的数据交

    换。它提供一个同步点,在这个同步点,两个线程可以交换彼此的数据。这两个线程通过

    exchange方法交换数据,如果第一个线程先执行exchange()方法,它会一直等待第二个线程也

    执行exchange方法,当两个线程都到达同步点时,这两个线程就可以交换数据,将本线程生产

    出来的数据传递给对方。

public class ExchangerTest {
    private static final Exchanger<String> exgr = new Exchanger<String>();
    private static ExecutorService threadPool = Executors.newFixedThreadPool(2);

    public static void main(String[] args) {
        threadPool.execute(new Runnable() {
            public void run() {
                try {
                    String A = "银行流水A"; // A录入银行流水数据
                    exgr.exchange(A);
                } catch (InterruptedException e) {
                }
            }
        });
        threadPool.execute(new Runnable() {
            public void run() {
                try {
                    String B = "银行流水B"; // B录入银行流水数据
                    String A = exgr.exchange("B");
                    System.out.println("A和B数据是否一致:" + A.equals(B) + ",A录入的是:"
                            + A + ",B录入是:" + B);
                } catch (InterruptedException e) {
                }
            }
        });
        threadPool.shutdown();
    }
}

原文地址:https://www.cnblogs.com/j-howie/p/10342002.html

时间: 2024-07-29 18:13:47

Java并发和高并发学习总结(四)- J.U.C之工具类的相关文章

JAVA学习第四十三课 — 集合框架工具类(一)

一.Collections:集合框架的工具类 其中的方法都是静态的 排序方法演示 import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; import java.util.List; class ComparaByLeng implements Comparator<String>{ public int compare(String o1, String o2) { int

大型电商分布式网站架构设计与实践,Java分布式架构,Java事务分布式高并发-视频教程

15套java架构师.集群.高可用.高可扩 展.高性能.高并发.性能优化.Spring boot.Redis.ActiveMQ.Nginx.Mycat.Netty.Jvm大型分布 式项目实战视频教程 视频课程包含: 高级Java架构师包含:Spring boot.Spring  cloud.Dubbo.Redis.ActiveMQ.Nginx.Mycat. Spring.MongoDB.ZeroMQ.Git.Nosql.Jvm.Mecached.Netty.Nio.Mina.性能调优.高并发.

Java线程测试高并发

package com.expai.utils; import java.io.BufferedReader; import java.io.InputStreamReader; import java.io.PrintWriter; import java.net.HttpURLConnection; import java.net.URL; import java.util.concurrent.CyclicBarrier; import java.util.concurrent.Execu

Java多线程与高并发:高并发解决思路

Java多线程与高并发:高并发解决思路 小玲子之凌空蹈虚关注 122018.11.21 09:55:30字数 1,553阅读 4,228 來源:http://www.wangtianyi.top/blog/2018/05/11/javaduo-xian-cheng-yu-gao-bing-fa-liu-gao-bing-fa-jie-jue-si-lu/ 缓存并发 image.png 当大量请求访问同一个没有被缓存的数据的时候,会发送大量请求给数据库,导致数据库压力过大,还会导致一致性问题,所以

【Unity 3D】学习笔记二十八:unity工具类

unity为开发者提供了很多方便开发的工具,他们都是由系统封装的一些功能和方法.比如说:实现时间的time类,获取随机数的Random.Range( )方法等等. 时间类 time类,主要用来获取当前的系统时间. using UnityEngine; using System.Collections; public class Script_04_13 : MonoBehaviour { void OnGUI() { GUILayout.Label("当前游戏时间:" + Time.t

java大数据 高并发 系统框架 springmvc mybatis Bootstrap html5 shiro maven SSM SSH

获取[下载地址]   QQ: 313596790   [免费支持更新]A 代码生成器(开发利器);全部是源码     增删改查的处理类,service层,mybatis的xml,SQL( mysql   和oracle)脚本,   jsp页面 都生成   就不用写搬砖的代码了,生成的放到项目里,可以直接运行B 阿里巴巴数据库连接池druid;  数据库连接池  阿里巴巴的 druid.Druid在监控.可扩展性.稳定性和性能方面都有明显的优势C 安全权限框架shiro ;  Shiro 是一个用

浅谈java中如何处理高并发的问题

1.从最基础的地方做起,优化我们写的代码,减少必要的资源浪费     a.避免频繁的使用new对象,对于整个应用只需要存在一个实例的类,我们可以使用单例模式.对于String连接操作,使用StringBuffer或StringBuilder,对于工具类可以通过静态方法来访问.     b.避免使用错误的方式,尽量不用instanceof做条件判断.使用java中效率高的类,比如ArrayList比Vector性能好. 2.html静态化     我们通过一个链接地址访问,通过这个链接地址,服务器

java 关于多线程高并发方面

转有关的文章链接: Java 高并发一:前言: http://www.jb51.net/article/92358.htm Java 高并发二:多线程基础详细介绍 http://www.jb51.net/article/92360.htm Java 高并发三:Java内存模型和线程安全详解 http://www.jb51.net/article/92361.htm Java 高并发四:无锁详细介绍 http://www.jb51.net/article/92362.htm Java 高并发五:J

java大数据 高并发 系统框架 springmvc mybatis Bootstrap html5 shiro maven SSM

获取[下载地址]   [免费支持更新]三大数据库 mysql  oracle  sqlsever   更专业.更强悍.适合不同用户群体[新录针对本系统的视频教程,手把手教开发一个模块,快速掌握本系统] A集成代码生成器 [正反双向(单表.主表.明细表.树形表,开发利器)+快速构建表单;freemaker模版技术 ,0个代码不用写,生成完整的一个模块,带页面.建表sql脚本,处理类,service等完整模块B 集成阿里巴巴数据库连接池druid;  数据库连接池  阿里巴巴的 druid.Drui