基础无论什么时候都是很重要的,为了防止长期也业务代码就此废掉,博主决定长期研究下多线程的java基础知识,算是巩固。本系列博文博主会不定期更新且长期更新下去,水平不够,如有发现不当之处欢迎批评指正,共同学习。
通过本文你可以了解到: 1、顺序执行线程的方式 2、多个任务终止的方法 3、线程池的工作原理或者线程复用的原理。
今天就来简单介绍Executor这个东西,这玩意是什么呢?官方注释说的很明白:Executes the given command at some time in the future!就是在将来的某个时候执行一个命令。很抽象?上代码就知道了这玩意就是一个接口:
public interface Executor {
void execute(Runnable command);
}
接口设计接单吧,无非就是提供了参数为Runnable的方法而已。就是一个接口而已,怎么实现还不是实现者说了算?(战略上藐视),那么你可以这么用它,:
//该代码来自Executor示例
class DirectExecutor implements Executor {
public void execute(Runnable r) {
r.run();
}
public void static main(String args[]){
DirectExecutor de = new DirectExecutor();
de.exectue(new Runnable() {
void run(){
System.out.println("哪个线程调用我,我就再哪个线程中执行")
}
});
}
}
那么如果执行一个比较耗时的任务呢?开启线程啊!多简单的事儿,所以上述代码改动如下:
class ThreadPerTaskExecutor implements Executor {
public void execute(Runnable r) {
//单独开启一个线程执行
new Thread(r).start();
}
public void static main(String args[]){
ThreadPerTaskExecutor tte = new ThreadPerTaskExecutor();
tte.exectue(new Runnable() {
void run(){
System.out.println("单独开启一个线程执行")
}
});
}
}
上面的代码逻辑很简单,就是每次执行exectue方法的时候都开启一个线程来执行Runnable。随着exectue的多次调用,会开启很多线程,而且这些线程执行的顺序也是不定的。
所以问题来了:如果设计一个多个异步任务顺序执行的框架呢?也就是说让多个线程顺序执行,该怎么设计?顺序执行,先进先出,那么脑海中的一个数据结构就是队列了,所以代码改动如下:
class SerialExecutor implements Executor{
//任务队列
final Queue tasks = new ArrayDeque();
//真正执行任务的代理对象
final Executor executor;
Runnable active;
SerialExecutor(Executor executor) {
this.executor = executor;
}
public void execute(final Runnable r) {
//将任务添加到队列中
tasks.add(new Runnable() {
public void run() {
try {
r.run();
} finally {
//当前任务执行完毕后,在执行队列中下一个任务
scheduleNext();
}
}
});
if (active == null) {
scheduleNext();
}
}
//从对列中获取任务并执行
protected void scheduleNext() {
if ((active = tasks.poll()) != null) {
executor.execute(active);
}
}
}
设计理念也很简单,将要执行的任务或者Runnable加入到一个队列中,每次从队列中去一个任务交给一个线程(在此处为ThreadPerTaskExecutor)出执行,注意这里并没有对队列做一个循环遍历操作,而是在run方法后加一个finally,执行scheduleNext来取队列中的下一个任务Runnable。
那么你就可以这么调用:
public static void main(){
SerialExecutor serialExecutor= new SerialExecutor(new ThreadPerTaskExecutor());
for(int i=0;i
关注
打赏
- Flutter之Widget构建过程详解
- Flutter之Widget 更新机制原理浅析
- 从源码角度分析android事件分发处理机制
- android事件拦截处理机制详解
- android 获取IP地址
- android 获取生肖和星座
- Android TextView setCompoundDrawables设置图片不显示解决方案
- Android Stuido集成LeakCanary编译失败TransformException、transformClassesWithDexBuilderForDebug
- Flutter实战之go_router路由组件入门指南
- HarmonyOS鸿蒙学习笔记(9)Navigator组件实现页面路由跳转