java核心知识点学习----创建线程的第三种方式Callable和Future CompletionService
前面已经指出通过实现Runnable时,Thread类的作用就是将run()方法包装成线程执行体,那么是否可以直接把任意方法都包装成线程执行体呢?Java目前不行,但其模仿者C#中是可以的.
Callabel接口可以看成是Runnable接口的增强版,只不过其线程执行体call()方法比run方法更加强大罢了:
>>call()方法中可以有返回值
>>call()方法中可以声明抛出异常.
一.创建线程的第三种方式----使用Callable对象进行创建
package com.amos.concurrent;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
/**
* @ClassName: CallableAndFuture
* @Description: 多线程中的Callable和Future学习
* @author: amosli
* @email:hi_amos@outlook.com
* @date Apr 22, 2014 12:07:26 AM
*/
public class CallableAndFuture {
public static void main(String[] args) throws Exception, ExecutionException {
ExecutorService newSingleThreadExecutor = Executors.newSingleThreadExecutor();
Future<String> future = newSingleThreadExecutor.submit(new Callable<String>() {
public String call() throws Exception {
Thread.sleep(20);
return "hi,amos";
}
});
// System.out.println("future:"+future.get(1,TimeUnit.MILLISECONDS));//等待指定的时间
System.out.println("future:" + future.get());
}
}
效果如下:
注:
1.这里要注意的是,创建线程时执行任务不是用execute()方法去执行了,而是用submit()方法.
2.同时要注意,这里call()方法返回值,要和上面的保持一致.
3.另外,可以设置最大等待时间,就是等待程序的返回值,这里使用get()方法.
4.其常用的其它方法有cancel(),isCancelled(),isDone(),分别表示取消关联的任务,是否已经取消,任务是否已经完成.
二.CompeltionService
CompeltionService主要用于提交一组Callable对象,其take方法用于返回已完成的callable任务的Future对象.可以用麦子收割来作比喻,种了10亩地的麦子,哪一块先成熟先收割哪一块.
举例:
package com.amos.concurrent; import java.util.Random;
import java.util.concurrent.Callable;
import java.util.concurrent.CompletionService;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorCompletionService;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class CallableAndFuture { public static void main(String[] args) throws Exception, ExecutionException {
ExecutorService newFixedThreadPool = Executors.newFixedThreadPool(10);
CompletionService<Integer> completionService = new ExecutorCompletionService<Integer>(newFixedThreadPool);
for(int i=0;i<11;i++){//创建10个任务
final int task=i;
completionService.submit(new Callable<Integer>() {//提交任务
public Integer call() throws Exception {
Thread.sleep(new Random().nextInt(3000));//最多3秒
return task;
}
});
}
//take
for(int i=0;i<11;i++){
System.out.println("已完成的任务:"+completionService.take().get());
}
}
效果如下图所示:
注:由结果也可以看出来,其随机结果是根据任务的先后完成顺序来的,使用其take()方法可以获取其返回结果.
java核心知识点学习----创建线程的第三种方式Callable和Future CompletionService的更多相关文章
- java核心知识点----创建线程的第三种方式 Callable 和 Future CompletionService
前面已经指出通过实现Runnable时,Thread类的作用就是将run()方法包装成线程执行体,那么是否可以直接把任意方法都包装成线程执行体呢?Java目前不行,但其模仿者C#中是可以的. Call ...
- Java反射机制(创建Class对象的三种方式)
1:了解什么是反射机制? 在通常情况下,如果有一个类,可以通过类创建对象:但是反射就是要求通过一个对象找到一个类的名称: 2:在反射操作中,握住一个核心概念: 一切操作都将使用Object完成,类 ...
- 创建线程的第三种方式——使用Callable接口
Callable是类似于Runnable的接口,实现Callable的类和实现Runnable的类都是可被其他线程执行的任务. 优点:有返回值 缺点:实现繁琐 简单实现: CallableAndFut ...
- Java核心知识点学习----线程中如何创建锁和使用锁 Lock,设计一个缓存系统
理论知识很枯燥,但这些都是基本功,学完可能会忘,但等用的时候,会发觉之前的学习是非常有意义的,学习线程就是这样子的. 1.如何创建锁? Lock lock = new ReentrantLock(); ...
- java核心知识点学习----并发和并行的区别,进程和线程的区别,如何创建线程和线程的四种状态,什么是线程计时器
多线程并发就像是内功,框架都像是外功,内功不足,外功也难得精要. 1.进程和线程的区别 一个程序至少有一个进程,一个进程至少有一个线程. 用工厂来比喻就是,一个工厂可以生产不同种类的产品,操作系统就是 ...
- Java核心知识点学习----使用Condition控制线程通信
一.需求 实现线程间的通信,主线程循环3次后,子线程2循环2次,子线程3循环3次,然后主线程接着循环3次,如此循环3次. 即:A->B->C---A->B->C---A-> ...
- Java核心知识点学习----多线程中的阻塞队列,ArrayBlockingQueue介绍
1.什么是阻塞队列? 所谓队列,遵循的是先进先出原则(FIFO),阻塞队列,即是数据共享时,A在写数据时,B想读同一数据,那么就将发生阻塞了. 看一下线程的四种状态,首先是新创建一个线程,然后,通过s ...
- java 中创建线程有哪几种方式?
Java中创建线程主要有三种方式: 一.继承Thread类创建线程类 (1)定义Thread类的子类,并重写该类的run方法,该run方法的方法体就代表了线程要完成的任务.因此把run()方法称为执行 ...
- Java反射机制(创建Class对象的三种方式)
1:SUN提供的反射机制的类: java.lang.Class<T> java.lang.reflect.Constructor<T> java.lang.reflect.Fi ...
随机推荐
- php接口和抽象类
接口关键字:interface,不加class关键字接口里面有成员方法,但是没有函数体.实现接口使用的关键字:implements 不是extends子类必须实现接口的所有方法 使用接口,你可以指定某 ...
- remote_addr和x_forwarded_for
做网站时经常会用到remote_addr和x_forwarded_for这两个头信息来获取客户端的IP,然而当有反向代理或者CDN的情况下,这两个值就不够准确了,需要调整一些配置. 什么是remote ...
- Kibana安装及部署
安装及部署 一.环境配置 操作系统:Cent OS 7 Kibana版本:3.1.2 JDK版本:1.7.0_51 SSH Secure Shell版本:XShell 5 二.操作过程 1.下载指定版 ...
- RESTClient使用
RESTClient使用
- 导入Eclipse工程 到 Android Studio
一.从Eclipse导入工程到Android Studio 根据官方的介绍,Android Studio可以兼容Eclipse的现有工程,但需要做一些操作: 首先升级ADT到最新版本,目前为版本号为2 ...
- [VB.NET]调用系统的文件夹选择对话框
以下示例代码展示如何调用系统的文件夹选择对话框: Private Function SelectFolder(ByVal Describe As String, Optional ByVal Show ...
- tinyxml学习5
读取和设置xml配置文件是最常用的操作,试用了几个C++的XML解析器,个人感觉TinyXML是使用起来最舒服的,因为它的API接口和Java的十分类似,面向对象性很好. TinyXML是一个开源的解 ...
- C#(Winform) Http 发送数据
Get方式 private string HttpGet(string url, string postData) { HttpWebRequest request = (HttpWebRequest ...
- jface的CheckboxTreeViewer实现单选
需求:使用FilteredTree实现一个下面这样的Dialog,要求Check框单选,即只能选择一个:当选择新的时候,旧的不选.说明:FilteredTree自带一个文本输入框. 1.自己的类继承o ...
- vbs下载文件
Dim Url,SavePath,FilenameUrl="http://www.kumi.cn/photo/43/7e/63/437e636e413071e3.jpg"SaveP ...