一 Concurrent.util常用类:

1. CyclicBarrier: 假设有场景:每个线程代表一个跑步运动员,当运动员都准备好后,才一起出发只要有一个人没有准备好,大家都等待。

import java.util.Random;
import java.util.concurrent.BrokenBarrierException;
import java.util.concurrent.CyclicBarrier;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors; public class UseCyclicBarrier { static class Runner implements Runnable {
private CyclicBarrier barrier;
private String name; public Runner(CyclicBarrier barrier, String name) {
super();
this.barrier = barrier;
this.name = name;
} @Override
public void run() {
try {
Thread.sleep(1000 * (new Random()).nextInt(5));
System.out.println(name + "准备OK");
barrier.await();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (BrokenBarrierException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println(name + "Go!");
}
}
public static void main(String[] args) {
CyclicBarrier barrier = new CyclicBarrier(3);
ExecutorService pool = Executors.newFixedThreadPool(3);
pool.execute(new Runner(barrier, "b1"));
pool.execute(new Runner(barrier, "b2"));
pool.execute(new Runner(barrier, "b3"));
pool.shutdown();
} }

运行结果:

b3准备OK

b2准备OK

b1准备OK

b2Go!

b1Go!

b3Go!

2. CountDownLacth:经常用于监听某些初始化操作,等初始化执行完毕后,通知主线程继续工作

import java.util.concurrent.CountDownLatch;

public class UseCountDownLatch {

	public static void main(String[] args) {
final CountDownLatch cDownLatch = new CountDownLatch(2);
Thread t1 = new Thread(new Runnable() { @Override
public void run() {
System.out.println("进入线程t1,等待其他线程处理完成...");
try {
cDownLatch.await();
//当CountDownLatch构造函数的参数减为0时,该线程才继续执行
System.out.println("t1线程继续执行...");
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}, "t1"); Thread t2 = new Thread(new Runnable() { @Override
public void run() {
System.out.println("t2线程执行初始化操作...");
try {
Thread.sleep(3000);
System.out.println("t2线程初始化操作完成,通知t1线程继续...");
cDownLatch.countDown();
//CountDownLatch构造函数的参数-1
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}, "t2");
Thread t3 = new Thread(new Runnable() { @Override
public void run() {
System.out.println("t3线程执行初始化操作...");
try {
Thread.sleep(4000);
System.out.println("t3线程初始化操作完成,通知t1线程继续...");
cDownLatch.countDown();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}, "t3");
t1.start();
t2.start();
t3.start();
} }

运行结果:

进入线程t1,等待其他线程处理完成...

t2线程执行初始化操作...

t3线程执行初始化操作...

t2线程初始化操作完成,通知t1线程继续...

t3线程初始化操作完成,通知t1线程继续...

t1线程继续执行...

区别:CyclicBarrier所有线程都阻塞;CountDownLatch只有一个(主)线程阻塞等待

3. Future和Callable:该模式非常适合在处理很耗时的业务逻辑时进行使用,可以有效的减少系统的响应时间,提高系统的吞吐量

public class UseFuture implements Callable<String>{
private String para; public UseFuture(String para) {
super();
this.para = para;
} public static void main(String[] args) throws InterruptedException, ExecutionException {
String querystr = "query";
//构造FutureTask,并且传入需要真正进行业务处理的类,该类实现了Callable接口
FutureTask<String> future = new FutureTask<>(new UseFuture(querystr));
FutureTask<String> future2 = new FutureTask<>(new UseFuture(querystr));
//创建一个固定线程数量的线程池
ExecutorService pool = Executors.newFixedThreadPool(2);
//这里提交任务的future,则开启线程执行RealData的call()
Future f = pool.submit(future);
Future f2 = pool.submit(future2);
//submit和execute的区别:submit可以实现calabale接口的对象;submit有返回值
System.out.println("请求完毕");
// while(true) {
//f.get()判断RealData是否执行完毕
// if(f.get() == null){
// System.out.println("---------------");
//future.get()获取ReadData
// System.out.println("数据:" + future.get());
// break;
// }
// }
try {
//处理其他实际业务逻辑
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println("数据:" + future.get());
System.out.println("数据:" + future2.get());
//并行处理,一共等待3秒
pool.shutdown();
} @Override
public String call() throws Exception {
//模拟执行耗时
Thread.sleep(3000);
String result = this.para + "处理完成";
return result;
} }

运行结果:

请求完毕

数据:query处理完成

数据:query处理完成

4. Semaphore信号量

Semaphore信号量非常适合高并发访问,新系统在上线之前,要对系统的访问量进行评估,当然这个值肯定不是随便拍拍脑袋就能想出来的,是经过以往的经验、数据、历年的访问量、以及推广粒力度进行的一个合理的评估,当然评估标准不能太大也不能太小,太大的话投入的资源达不到实际效果,浪费资源,太小的话,某个时间点一个峰值的访问量上来直接可以压垮系统。

相关概念:

  1. PV(Page View):网站的总访问量,页面浏览量或点击量,用户每刷新一次就会被记录一次
  2. UV(Unlque Visitor):访问网站的一台电脑客户端为一个访客,一般来讲,时间上以00:00-24:00之内相同IP的客户端只记录一次
  3. QPS(Query Per Second):每秒查询数,qps很大程度上代表了系统业务的繁忙程度,每次请求的背后,可能对应着多次磁盘IO,多次网络请求,多个cpu时间片等。我们通过qps可以非常直观的了解当前系统业务情况,一旦当前qps超过所设定的预警阀值,可以考虑增加机器对集群扩容,以免压力过大导致宕机,可以根据前期的压力测试得到估值,再结合后期综合运维情况,结算出阀值。
  4. RT(Response Time):请求的响应时间,这个指标非常关键,直接说明前期用户的体验,因此任何系统设计师都想降低rt时间。
  5. 当然还涉及到cpu、内存、网络、磁盘等情况,更细节的问题很多,如select、update、delete/ps等数据库层面的统计。

应对高并发环境:

  1. 网络层面
  2. 服务层面:多台ng服务器做分流负载均衡
  3. Java业务上进行模块化划分

常用Concurrent.util包工具类——高并发的更多相关文章

  1. (转载)分享常用的GoLang包工具

    分享常用的GoLang包工具 包名 链接地址 备注 Machinery异步队列 https://github.com/RichardKnop/machinery Mqtt通信 github.com/e ...

  2. Concurrent包工具类使用

    一.读写锁 传统的同步锁就是独占式锁,当线程使用资源时候保持独占,无论读写.当人们发现请求队列(假设)中相邻请求为读-读的时候,阻塞是一种浪费资源的操作.比如公告板,所有路过的人(请求)都是读操作,并 ...

  3. Java 操作jar包工具类以及如何快速修改Jar包里的文件内容

    需求背景:写了一个实时读取日志文件以及监控的小程序,打包成了Jar包可执行文件,通过我们的web主系统上传到各个服务器,然后调用ssh命令执行.每次上传前都要通过解压缩软件修改或者替换里面的配置文件, ...

  4. Android util.Log 工具类

    Android中的日志工具类是Log(android.util.Log),这个类中提供了如下5个方法来供我们打印日志. Log.v().用于打印那些最为琐碎的.意义最小的日志信息.对应级别verbos ...

  5. Java中 util 包 Calendar类制作万年历(不用自己写方法,直接用Java写好的包中的类的方法)

    代码前需要了解的关于Calendar类的内容:      1.在util包中,首先要知道Calendar 提供了一个类方法 getInstance,以获得此类型的一个通用的对象.Calendar 的 ...

  6. java常用加密和解密工具类EncryptUtil.java

    package cn.util; import java.io.UnsupportedEncodingException; import java.security.MessageDigest; im ...

  7. java.util.Properties工具类

    import java.io.FileNotFoundException; import java.io.FileWriter; import java.io.IOException; import ...

  8. PHP常用之封装分页工具类

    分页基本上是每个项目都会使用到的,所以呢,把它封装成一个工具类,以后直接调用就可以了(虽然TP框架的灰常强大,但是自己封一个也未尝不可.),这样既省时又省力还赚'工分'. 我封的这个分页工具类还比较完 ...

  9. Thinkphp5 用ab压力测试工具测试高并发请求

    上篇文章[Thinkphp5实现悲观锁]已介绍过thinkphp5使用悲观锁实现高并发的场景,这篇文章将实际测试下. 在shell里进入到apache的bin目录,输入以下url: ab -n 100 ...

随机推荐

  1. pandas模块之读取文件

    首先我们来看一个文件 1 男 北京 刘一 我笑 #跳过此行,序号1 2 女 上海 刘珊 你笑 3 男 杭州 刘五 他笑 #跳过此行,序号四 4 女 重庆 刘六 不笑了 下面来分析内容,并使用参数 1 ...

  2. java获取当月日期 和 周末

    /** * java获取 当月所有的日期集合 * @return */public static List<Date> getDayListOfMonth() { List list = ...

  3. Java反射学习-4 - 反射调用方法

    反射调用方法: package cn.tx.reflect; import java.lang.reflect.Constructor; import java.lang.reflect.Method ...

  4. 10.18.2 linux文件压缩与打包

    tar压缩工具 tar 本身为一个打包工具,可以把目录打包成一个文件,它的好处是它把所有文件整合成一个大文件整体,方便拷贝或者移动. 语法:tar [-zjxcvfpP] filename tar 命 ...

  5. php开发面试题---日常面试题1

    php开发面试题---日常面试题1 一.总结 一句话总结: 实战确定学习方向,然后去网上找视频资源,非常多,然后看书 1.什么样的数据存在memcache里面? 要去数据库里面查询的那些数据,数据库查 ...

  6. SVG开发包, 20 个有用的 SVG 工具,提供更好的图像处理

    20 个有用的 SVG 工具,提供更好的图像处理 SVG 现正在 Web 设计领域变得越发流行, 你可以使用 Illustrator 或者 Inkscape 来创建 SVG 图像. 但当进行 Web ...

  7. TypeScript躬行记(5)——类型兼容性

    TypeScript是一种基于结构类型的语言,可根据其成员来描述类型.以结构相同的Person接口和Programmer类为例,如下所示. interface Person { name: strin ...

  8. laravel 简单应用 redis

    1.连接配置 database.php 中 测试用 都没做修改 2.创建测试路由及控制器 //添加路由 Route::get('testRedis','RedisController@testRedi ...

  9. shell zip和unzip压缩和解压,压缩效率

    1.把/home目录下面的mydata目录压缩为mydata.zip zip -r mydata.zip mydata #压缩mydata目录zip -r mydata.zip ./*txt #压缩当 ...

  10. MongoDB简单认识

    MongoDB 为何物 NoSQL 泛指非关系型数据库,该词是关系型数据库(即 SQL)的相对称呼.MongoDB 是非关系型数据库中较为人熟知的一种. 它拥有很多优秀特性,例如高性能.高可用.支持丰 ...