threadpoolexecutor中的submit()方法详细讲解-亚博电竞手机版

目录

  • submmit()参数解析
  • submit()的返回值future
  • futuretask的get()的实现
  • submit()使用案例

在使用线程池的时候,发现除了execute()方法可以执行任务外,还发现有一个方法submit()可以执行任务。

submit()有3个参数不一的方法,这些方法都是在executorservice接口中声明的,在abstractexecutorservice中实现,而threadpoolexecutor继承abstractexecutorservice。

future submit(callable callable); future submit(runnable var1, t result); future submit(runnable runnable);

我们可以看到submit()的参数既可以是run恰卡编程网nable,又可以是callable。对于runnable我们是比较熟的,它是线程thread所执行的任务,里面有一个run()方法,是任务的具体执行操作。那么callable呢?我们一起看下他们的代码吧。

public interface runnable { void run(); } public interface callable { v call() throws exception; }

runnable这里就不介绍了,callable接口定义了一个call()方法,返回一个callable指定的泛型类,并且call()调用的时候会抛出异常。通过比较runnable和callable还看不什么端倪,那么我们就看看内部实现吧。

submmit()参数解析

这里重点分析submit()带参数runnable和callable的方法

public future&l leaked interrupts int s = state; if (s >= interrupting) handlepossiblecancellationinterrupt(s); } }

我们在new futuretask()对象的时候,在futuretask构造方法中会对state状态赋值为new,并且传入一个callable对象。通过futuretask的run()我们可以知道,其实就通过state状态判断,调用callable的call()。(如果传入的参数是runnable,runnable在runnableadapter类中转化时,在call()中,其实调用的就是runnable的run()方法)。

所以在submit()方法中,调用了一个execute(task)的方法,实际执行的是futuretask的run(),而futuretask的run()调用的是callable的call()方法。

说了这么多,submit()最后执行的还是传入的runnable的run()或callable的call()方法。好像没有futuretask什么事啊。

其实不是,submit()返回futuretask对象,通过这个futuretask对象调用get()可以返回submit()方法传入的一个泛型类参数result对象,如果是callable直接通过call()返回。这个返回值的可以用来校验任务执行是否成功。

futuretask的get()的实现

public v get() throws interruptedexception, executionexception { int s = state; if (s <= completing) s = awaitdone(false, 0l); //等待任务执行完 return report(s);//将执行的任务结果返回 } private v report(int s) throws executionexception { object x = outcome; if (s == normal) return (v)x; if (s >= cancelled) throw new cancellationexception(); throw new executionexception((throwable)x); }

最后是通过outcome参数将根据任务的状态将结果返回。那么outcome参数在哪里赋值了?outcome参数赋值的地方有好2处,一是futuretask的set(),二是futuretask的setexception()。

set()是在futuretask的run()执行完成后,将传入的result参数赋值给传入给set(),赋值给outcome参数。如果run()报异常了会将throwable对象通过setexception()方法传入,赋值给outcome变量

大家可以返回上面的run()查看下。

protected void set(v v) { if (u.compareandswapint(this, state, new, completing)) { outcome = v; u.putorderedint(this, state, normal); // final state finishcompletion(); } } protected void setexception(throwable t) { if (u.compareandswapint(this, state, new, completing)) { outcome = t; u.putorderedint(this, state, exceptional); // final state gseyvs finishcompletion(); } }

submit()使用案例

public class test { private static final string success = "success"; public static void main(string[] args) { executorservice executorservice = executors.newfixedthreadpool(3); system.out.println("------------------任务开始执行---------------------"); future future = executorservice.submit(new callable() { @override public string call() throws exception { thread.sleep(5000); system.out.println("submit方法执行任务完成" " thread name: " thread.currentthread().getname()); return success; } }); try { string s = future.get(); if (success.equals(s)) { string name = thread.currentthread().getname(); system.out.println("经过返回值比较,submit方法执行任务成功 thread name: " name); } } catch (interruptedexception e) { e.printstacktrace(); } catch (executionexception e) { e.printstacktrace(); } system.out.println("-------------------main thread end---------------------"); } }

打印结果:

------------------任务开始执行---------------------

call()调用开始: 1496899867882

submit方法执行任务完成: 1496899872897 thread name: pool-1-thread-1

经过返回值比较,submit方法执行任务成功 thread name: main

-------------------main thread end---------------------

主线程会一直阻塞,等待线程池中的任务执行完后,在执行后面的语句。

到此这篇关于threadpoolexecutor中的submit()方法详细讲解的文章就介绍到这了,更多相关threadpoolexecutor submit()方法内容请搜索我们以前的文章或继续浏览下面的相关文章希望大家以后多多支持我们!

展开全文
内容来源于互联网和用户投稿,文章中一旦含有亚博电竞手机版的联系方式务必识别真假,本站仅做信息展示不承担任何相关责任,如有侵权或涉及法律问题请联系亚博电竞手机版删除

最新文章

网站地图