在阅读ZooKeeper的源码时,看到这么一个片段,在单机模式启动的时候,会调用下面的方法,根据zoo.cfg的配置启动单机版本的服务器:

public void runFromConfig(ServerConfig config) throws IOException {
//1 创建ZooKeeper服务器
final ZooKeeperServer zkServer = new ZooKeeperServer();
final CountDownLatch shutdownLatch = new CountDownLatch(1);
zkServer.registerServerShutdownHandler(
new ZooKeeperServerShutdownHandler(shutdownLatch));
...
//2 创建ZooKeeper的NIO线程
cnxnFactory = ServerCnxnFactory.createFactory();
cnxnFactory.configure(config.getClientPortAddress(),
config.getMaxClientCnxns());
cnxnFactory.startup(zkServer); // 3 调用shutdownLatch阻塞,服务器在新线程正常处理请求
shutdownLatch.await();
// 4 如果有错误,直接调用shutdown
shutdown();
// 5 执行cnx.join()等待NIO线程关闭
cnxnFactory.join();
if (zkServer.canShutdown()) {
zkServer.shutdown(true);
}
}
...
protected void shutdown() {
if (cnxnFactory != null) {
cnxnFactory.shutdown();
}
}

其中比较有意思的两个地方:

1 CountDownLatch的使用

开启NIO新线程接收客户端的请求,服务端的主线程直接利用countdownlatch挂起。这个CountDownLatch之前有说过,就是个多线程的计数器。

详细内容参考文章——Java计数器之CountDownLatch、CyclicBarrier、Semaphore

2 join的作用

join的作用就是主线程遇到A.join()之后,就会挂起;登到A结束后,才会继续执行。可以理解为主线程调用了A的wait方法...

下面有个Join的小例子:

public class JoinTest {
public static void main(String[] args) throws InterruptedException {
Thread A = new Thread(()->{
System.out.println("进入线程A");
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("A:线程A结束");
});
A.start(); System.out.println("Main:等待线程A结束");
A.join();
System.out.println("Main:线程A已经结束,退出");
}
}

输出内容为:

Main:等待线程A结束
进入线程A
A:线程A结束
Main:线程A已经结束,退出

可以看到,Main线程在A.join()的地方挂起了。等A结束后,才继续执行。

ZooKeeper这样的设计,使服务器在关闭前,确保NIO线程正确关闭,避免NIO资源的未释放。

跟着ZooKeeper学Java——CountDownLatch和Join的使用的更多相关文章

  1. 从零开始学 Java - 我放弃了 .NET ?

    这不是一篇引起战争的文章 毫无疑问,我之前是一名在微软温暖怀抱下干了近三年的 .NET 开发者,为什么要牛(sha)X一样去搞 Java 呢?因为我喜欢 iOS 阿!哈哈,开个玩笑.其实,开始学 Ja ...

  2. JAVA多线程之CountDownLatch与join的区别

    首先,我们来看一个应用场景1: 假设一条流水线上有三个工作者:worker0,worker1,worker2.有一个任务的完成需要他们三者协作完成,worker2可以开始这个任务的前提是worker0 ...

  3. 2018年如何快速学Java

    前言 只有光头才能变强 提前预警:本文适合Java新手阅读(老手可在评论区给下建议),希望大家看完能有所收获. 一.为什么我要写下这篇文章 1.1直接缘由: 在今天(2018年11月4日)有个同学给我 ...

  4. 学大数据是先学java还是先学python?

    大数据的发展趋势日渐明显,但是进入这个领域的门槛不小,除了要有心理准备,其次就是要付诸实际行动中去学习. 学习方法有很多,在没有基础的前提下,自学是因人而异是有难度.其次是大数据目前的工作方向主要是三 ...

  5. Linux -- 基于zookeeper的java api(二)

    Linux -- 基于zookeeper的java api(二) 写一个关于基于集群的zookeeper的自定义实现HA 基于客户端和监控器:使用监控的方法查看每个注册过的节点的状态来做出操作. Wa ...

  6. CountDownLatch与join的区别和联系

    首先,我们来看一个应用场景1: 假设一条流水线上有三个工作者:worker0,worker1,worker2.有一个任务的完成需要他们三者协作完成,worker2可以开始这个任务的前提是worker0 ...

  7. Java学习路线图(如何快速学Java)

    不知不觉从初学Java到现在已经8年了,今天在这里给刚入门和入门不久的小伙伴们一些建议.可能总结的不是很详细,但给出了一个大概的学习路线.希望对大家有帮助哈~ 如何快速学Java 这里我以Java E ...

  8. 教妹学 Java:晦涩难懂的泛型

    00.故事的起源 “二哥,要不我上大学的时候也学习编程吧?”有一天,三妹突发奇想地问我. “你确定要做一名程序媛吗?” “我觉得女生做程序员,有着天大的优势,尤其是我这种长相甜美的.”三妹开始认真了起 ...

  9. 我的那些年(12)~公司技术转行,我也跟着转到java了

    回到目录 我的那些年(12)~公司技术转行,我也跟着转到java了 CTO换人了 微软技术栈不被认可经常被喷 技术统一向java转 换了mac book后,docker还是很占内存 学习springb ...

随机推荐

  1. centos环境自动化批量安装jdk软件脚本

    自动化安装jdk软件部署脚本 准备工作: 1.在执行脚本的服务器上生成免密码公钥: 安装expect命令 yum install -y expect ssh-keygen 三次回车 2.将jdk-7u ...

  2. asp.net core 通过ajax上传图片及wangEditor图片上传

    asp.net core 通过ajax上传图片 .net core前端代码,因为是通过ajax调用,首先要保证ajax能调用后台代码,具体参见上一篇.net core 使用ajax调用后台代码. 前端 ...

  3. jq中Deferred对象的使用

    var d=$.Deferred(); //deferred下面的方法有: // ["resolve", "resolveWith", "reject ...

  4. hdu2586 lca倍增法

    倍增法加了边的权值,bfs的时候顺便把每个点深度求出来即可 #include<iostream> #include<cstring> #include<cstdio> ...

  5. python接口自动化测试九:重定向相关

    allow_redirects=False  不重定向 # 获取重定向后的地址 loc = r.headers # 相对地址 host = 'https://i.cnblogs.com/' url = ...

  6. Sony笔记本

    关机的情况下按键盘 f2键.进菜单选更改 bios设置 修改 3个地方 进bios右移 boot上 第一项 ufei改成 legacy external device改成enabled 下面启动顺序改 ...

  7. checkbox简单例子

    写个简单的例子,如下:html页面部分:<input type="checkbox" value="1" name="check"/& ...

  8. 2018-2019-2 网络对抗技术 20165333 Exp1 PC平台逆向破解

    1 逆向及Bof基础实践说明 1.1 实践目标 本次实践的对象是一个名为pwn1的linux可执行文件.该程序正常执行流程是:main调用foo函数,foo函数会简单回显任何用户输入的字符串.该程序同 ...

  9. vim的基本用法

  10. SpringBank 开发日志 一种简单的拦截器设计实现

    当交易由Action进入Service之前,需要根据不同的Service实际负责业务的不同,真正执行Service的业务逻辑之前,做一些检查工作.这样的拦截器应该是基于配置的,与Service关联起来 ...