异步框架asyn4j的原理
启动时调用init方法
- public void init(){
- if (!run){
- run = true;
- //工作队列
- workQueue = newPriorityBlockingQueue(maxCacheWork);
- //是否存在工作队列满处理类
- if (this.workQueueFullHandler != null) {
- //自定义线程池
- workExecutor = newAsynThreadPoolExecutor(work_thread_num, work_thread_num, 0L,TimeUnit.MILLISECONDS,
- workQueue, new AsynThreadFactory(),new AsynWorkRejectedExecutionHandler(this.workQueueFullHandler),
- executeWorkNum);
- } else {
- workExecutor = newAsynThreadPoolExecutor(work_thread_num, work_thread_num, 0L,TimeUnit.MILLISECONDS,
- workQueue, new AsynThreadFactory(),executeWorkNum);
- }
- //回调函数工作队列
- callBackQueue = newLinkedBlockingQueue();
- //自定义回调函数线程池
- callBackExecutor = newCallBackThreadPoolExecutor(callback_thread_num, callback_thread_num, 0L,
- TimeUnit.MILLISECONDS, callBackQueue,new CallBackThreadFactory(),
- new CallBackRejectedExecutionHandler(),callBackNum);
- //service启动和关闭处理器
- if (this.serviceHandler != null) {
- this.serviceHandler.setServiceStat(0);
- this.serviceHandler.setAsynService(this);
- this.serviceHandler.process();
- }
- //启动工作队列满处理器
- if (this.workQueueFullHandler != null) {
- this.workQueueFullHandler.process();
- }
- //程序关闭后的处理
- Runtime.getRuntime().addShutdownHook(newThread(){
- public void run()
- {
- AsynServiceImpl.this.close(AsynServiceImpl.closeServiceWaitTime);
- }
- });
- }
- }
AsynServiceImpl主要有两个线程池和三个处理器组成
工作线程池AsynThreadPoolExecutor
- public classAsynThreadPoolExecutor
- extends ThreadPoolExecutor
- {
- private AtomicLong executeWorkNum;
回调函数线程池CallbackThreadPoolExecutor
- public classCallBackThreadPoolExecutor
- extends ThreadPoolExecutor
- {
- private AtomicLong callBackNum;
AsynThreadPoolExecutor的executeWorkNum,统计任务的执行数
AsynThreadPoolExecutor的callBackNum,统计回调函数的执行数
ServiceHandler处理器(启动或关闭)
WorkQueueFullHandler处理器(任务数超过maxCacheWork)
ErrorAsynWorkHandler处理器(任务执行异常)
执行时调用addWork方法
- public void addWork(Object tagerObject, Stringmethod, Object[] params, AsynCallBack asynCallBack, WorkWeight weight, booleancache)
- {
- if ((tagerObject == null) || (method ==null)) {
- throw newIllegalArgumentException("target name is null or target method name is null");
- }
- Object target = null;
- //如果对象是String
- if(tagerObject.getClass().isAssignableFrom(String.class)){
- addWorkWithSpring(tagerObject.toString(),method, params, asynCallBack, weight);
- return;
- }
- //如果对象是class
- if ((tagerObject instanceof Class)) {
- String classKey =((Class)tagerObject).getSimpleName();
- //是否缓存,一个class缓存一个默认的对象,防止重复创建
- if (cache)
- {
- target = targetCacheMap.get(classKey);
- if (target == null)
- {
- target =newObject((Class)tagerObject);
- targetCacheMap.put(classKey, target);
- }
- }
- else
- {
- target = newObject((Class)tagerObject);
- }
- }
- else
- {
- target = tagerObject;
- }
- if (target == null) {
- throw newIllegalArgumentException("target object is null");
- }
- //封装成异步任务
- AsynWork anycWork = newAsynWorkEntity(target, method, params, asynCallBack, weight);
- addAsynWork(anycWork);
- }
- public voidaddAsynWork(AsynWork asynWork){
- if (!run) {
- throw new Asyn4jException("asynservice is stop or no start!");
- }
- if (asynWork == null) {
- throw newIllegalArgumentException("asynWork is null");
- }
- try<span style="font-family: Arial, Helvetica, sans-serif;">{</span>
- //通过semaphore来获取许可权限
- if(this.semaphore.tryAcquire(addWorkWaitTime, TimeUnit.MILLISECONDS))
- {
- WorkProcessor workProcessor = newWorkProcessor(asynWork, this);
- workExecutor.execute(workProcessor);
- totalWork.incrementAndGet();
- }
- else{
- log.warn("work queue is full,addwork to cache queue");
- this.workQueueFullHandler.addAsynWork(asynWork);
- }
- }
- catch (InterruptedException e)
- {
- log.error(e);
- }
- }
通过semaphore来控制最大的访问线程数,maxCacheWork就是semaphore的数量,也是工作队列的数量
这里的目的是控制工作队列的数量不能超过maxCacheWork(也可以通过用上限的queue来代替)
如果超过队列maxCacheWork,就用workQueueFullHandler去处理,处理方式同线程池的拒绝策略处理器(
newAsynWorkRejectedExecutionHandler(this.workQueueFullHandler))不过线程池的拒绝策略没用到(前提是队列的有上限的队列),
工作任务WorkProcessor(内含AsynWorkEntity)
- public void run() {
- Thread currentThread =Thread.currentThread();
- if (this.asynWork.getThreadName() != null){
- setName(currentThread,this.asynWork.getThreadName());
- }
- AsynCallBack result = null;
- try{
- result = this.asynWork.call();
- if (result != null) {
- ApplicationContext.getCallBackExecutor().execute(result);
- }
- }
- catch (Throwable throwable){
- if(this.applicationContext.getErrorAsynWorkHandler() != null) {
- this.applicationContext.getErrorAsynWorkHandler().addErrorWork(this.asynWork,throwable);
- }
- }
- finally{
- this.applicationContext.getSemaphore().release();
- }
- }
首先修改线程名称,然后调用asynWork的call方法,如果有回调函数,就执行,如果有异常就执行ErrorAsynWorkHandler,最后Semaphore释放一个许可
AsynWorkEntity
- public AsynCallBack call()
- throws Exception {
- if (this.target == null) {
- throw new RuntimeException("targetobject is null");
- }
- Class clazz = this.target.getClass();
- String methodKey =MethodUtil.getClassMethodKey(clazz, this.params, this.method);
- Method targetMethod =(Method)methodCacheMap.get(methodKey);
- if (targetMethod == null){
- targetMethod =MethodUtil.getTargetMethod(clazz, this.params, this.method);
- if (targetMethod != null) {
- methodCacheMap.put(methodKey,targetMethod);
- }
- }
- if (targetMethod == null) {
- throw newIllegalArgumentException("target method is null");
- }
- Object result =targetMethod.invoke(this.target, this.params);
- if (this.anycResult != null) {
- this.anycResult.setInokeResult(result);
- }
- return this.anycResult;
- }
通过反射技术调用用具体方法,也用缓存技术,anycResult就是你定义的回调函数,没有就返回null
关闭时调用close方法
- publicvoid close(long waitTime){
- if (run){
- run = false;
- try {
- workExecutor.awaitTermination(waitTime,TimeUnit.MILLISECONDS);
- callBackExecutor.awaitTermination(0L,TimeUnit.MILLISECONDS);
- }
- catch (InterruptedException e)
- {
- log.error(e);
- }
- //关闭工作线程和回调函数线程
- workExecutor.shutdown();
- callBackExecutor.shutdown();
- //service关闭处理器
- if (this.serviceHandler != null)
- {
- this.serviceHandler.setAsynWorkQueue(workQueue);
- this.serviceHandler.setCallBackQueue(callBackQueue);
- this.serviceHandler.setServiceStat(1);
- this.serviceHandler.process();
- }
- }
- }
异步框架asyn4j的原理的更多相关文章
- jQuery异步框架探究1:jQuery._Deferred方法
jQuery异步框架应用于jQuery数据缓存模块.jQuery ajax模块.jQuery事件绑定模块等多个模块,是jQuery的基础功能之中的一个.实际上jQuery实现的异步回调机制能够看做ja ...
- 《HiWind企业快速开发框架实战》(1)框架的工作原理
<HiWind企业快速开发框架实战>(1)框架的工作原理 1.HiWind架构 HiWind的基本架构如下: 持久层部分:同时为框架本身的业务服务,也为开发人员的自定义业务服务. 逻辑层: ...
- 无废话Android之内容观察者ContentObserver、获取和保存系统的联系人信息、网络图片查看器、网络html查看器、使用异步框架Android-Async-Http(4)
1.内容观察者ContentObserver 如果ContentProvider的访问者需要知道ContentProvider中的数据发生了变化,可以在ContentProvider 发生数据变化时调 ...
- Spring框架和MVC原理
Spring框架和MVC原理 目录 Spring框架 SpringMVC工作原理 参考资料 回到顶部 Spring框架 Spring当前框架有20个jar包,大致可以分为6大模块: Core Cont ...
- Android 异步框架 RxJava2
观察者模式的概念 RxJava是android的异步框架,官方介绍是可观测的序列,组成异步基于事件程序的库.特点是观察者模式,基于事件流的链式调用,随着异步操作调度过程复杂的情况下,程序逻辑也变得越来 ...
- php框架的制作原理
php框架的制作原理 (2012-08-16 14:25:55) 转载▼ 标签: php框架制作 杂谈 分类: php index.php 主入口文件 <?php define('ISEXIS ...
- 基于SEDA的异步框架设计与实现
基于SEDA的异步框架设计与实现 二.为什么使用SEDA 目前,面对并发环境,主流互联网服务器编程模型有两种:多线程模型以及事件驱动模型.但是这两个模型都不足以解决这个问题.我们来首先看一下这两种编程 ...
- SpringBoot系列之日志框架介绍及其原理简介
SpringBoot系列之日志框架介绍及其原理简介 1.常用日志框架简介 市面上常用日志框架:JUL.JCL.jboss-logging.logback.log4j.log4j2.slf4j.etc. ...
- php面试专题---21、MVC框架基本工作原理考察点
php面试专题---21.MVC框架基本工作原理考察点 一.总结 一句话总结: 会的东西快速过,不要浪费时间,生命有限,都是一些很简单的东西. 1.mvc框架单一入口的 优势 是什么? 可以进行统一的 ...
随机推荐
- Delphi操作Excel大全
Delphi操作Excel大全 DELPHI操作excel(转)(一) 使用动态创建的方法 首先创建 Excel 对象,使用ComObj:var ExcelApp: Variant;ExcelApp ...
- ACM/ICPC 之 BFS-广搜进阶-八数码(经典)(POJ1077+HDU1043)
八数码问题也称为九宫问题.(本想查查历史,结果发现居然没有词条= =,所谓的历史也就不了了之了) 在3×3的棋盘,摆有八个棋子,每个棋子上标有1至8的某一数字,不同棋子上标的数字不相同.棋盘上还有一个 ...
- 1.JS设计模式-this,call&apply
1. this,call&apply 1.1 this this是Javascript语言的一个关键字. 它代表函数运行时,自动生成的一个内部对象,只能在函数内部使用. 1.1.1 普通函数调 ...
- InnoDB O_DIRECT选项漫谈(一)【转】
本文来自:http://insidemysql.blog.163.com/blog/static/2028340422013671186977/ 最近和文件系统内核开发人员做技术交流,对O_DIR ...
- 【剑指offer】题目20 顺时针打印矩阵
输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下矩阵: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 则依次打印出 ...
- HTML标记语法之表格元素
语法与语义: <table>和</table>定义表格的开始和结束 <thead>和</thead>定义表格头部的开始和结束 <tbody> ...
- C 替换字符方法--1
#include "stdafx.h" //linux 底下要去掉这一行 #include <stdio.h> #include<stdlib.h> #in ...
- Windows 10 周年更新正式版下载 + win10 快捷键
Windows 10 周年更新正式版 360云资源总汇(施工中): https://yunpan.cn/c6Svi7Az52XBs (提取码:e5dd)今后提到周年更新版.1607版或RS1版,都是 ...
- Qt Designer 修改窗体大小改变控件位置
一.新建一个窗体 用qt designer 新建一个QWidget窗体, 在窗体中右键 选择布局, 发现布局是选择不了的,这个是因为窗体里面没有添加控件, 任意添加空间后便可选择 右键-- 布局-- ...
- settimeout,cleartimeout的使用分析
设置时间的定时轮回执行,大家想到的js也就是settimeout这个方法,这个方法确实能够实现定时反复执行的功能,clearttimeout这是清理或者是暂停轮回执行的情况.可是发现clearttim ...