第三部分-并发设计模式34:WorkThread 设计模式
1.WorkThread 设计模式
可以有效避免频繁创建,销毁以及OOM问题
2.类比现实
类比车间的工作模式
车间工人,有活大家一起干,没活就聊聊天
车间里工人的数量是确定的
3.编程世界映射车间的套路呢
如何实现Worker Thread模式
阻塞队列做任务池,创建固定数量的线程消费阻塞队列。
这个方案就是线程池方案
4.线程池方案,解决Thread-Per-Message的问题
伪代码
ExecutorService es = Executors
.newFixedThreadPool(500);
final ServerSocketChannel ssc =
ServerSocketChannel.open().bind(
new InetSocketAddress(8080));
//处理请求
try {
while (true) {
// 接收请求
SocketChannel sc = ssc.accept();
// 将请求处理任务提交给线程池
es.execute(()->{
try {
// 读Socket
ByteBuffer rb = ByteBuffer
.allocateDirect(1024);
sc.read(rb);
//模拟处理请求
Thread.sleep(2000);
// 写Socket
ByteBuffer wb =
(ByteBuffer)rb.flip();
sc.write(wb);
// 关闭Socket
sc.close();
}catch(Exception e){
throw new UncheckedIOException(e);
}
});
}
} finally {
ssc.close();
es.shutdown();
}
5.创建线程池的正确姿势
java线程池可以避免无限制的创建线程导致OOM
也可以避免无限制的接受任务导致OOM(线程池指定游街队列接受任务)
当请求量大于有界队列容量时,就合理的拒绝请求。同时创建时,要给线程赋予一个业务相关的名字
范例
ExecutorService es = new ThreadPoolExecutor(
50, 500, 60L, TimeUnit.SECONDS,
//注意要创建有界队列
new LinkedBlockingQueue(2000),
//建议根据业务需求实现ThreadFactory
r->{
return new Thread(r, "echo-"+ r.hashCode());
},
//建议根据业务需求实现RejectedExecutionHandler
new ThreadPoolExecutor.CallerRunsPolicy());
6.注意事项
提交到相同线程池中的任务一定是相互独立的,最好不要相互依赖
7.总结
Worker-Thread 其实也是一种分工模式
Thread-Pre-Message 类比现实中的委托他人办理
Worker-Thread 类似车间工人的工作模式
Worker-Thread 能避免线程频繁创建,销毁,而且可以限制线程的最大数量。java语言可以直接使用线程池实现WorkerThread模式,线程池是一个基础及优秀的工具类。大厂是不允许使用new Thread()来创建线程的,必须用线程池。
8.扩展
// 只有一个线程的线程池
ExecutorService pool = Executors.newSingleThreadExecutor();
原创:做时间的朋友
分类:
java并发
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· 没有源码,如何修改代码逻辑?
· 分享4款.NET开源、免费、实用的商城系统
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
· 记一次.NET内存居高不下排查解决与启示