`
conkeyn
  • 浏览: 1529323 次
  • 性别: Icon_minigender_1
  • 来自: 厦门
社区版块
存档分类
最新评论

java利用FutureTask、ExecutorService 在多核时代充分利用CPU运算

    博客分类:
  • Java
阅读更多

转自:http://hi.baidu.com/ecspell/blog/item/024e37fa87b0cf849e5146b0.html


FutureTask、 ExecutorService 相关知识,请看java,API

一个使用FutureTask简单的例子:

package com.spell.threads;

import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.FutureTask;

/**
 * 测试FutureTask的用法,如果不想分支线程阻塞主线程,又想取得分支线程的执行结果,就用FutureTask
 *
 * @author Administrator
 *
 */
public class FutureTaskTest {

 /**
  * @param args
  */
 public static void main(String[] args) {
  CountNum cn = new CountNum(0);
  //FutureTask<Integer> 这里的表示返回的是Integer
  FutureTask<Integer> ft = new FutureTask<Integer>(cn);
  Thread td = new Thread(ft);
  System.out.println("futureTask开始执行计算:" + System.currentTimeMillis());
  td.start();
  System.out.println("main 主线程可以做些其他事情:" + System.currentTimeMillis());
  try {
   // futureTask的get方法会阻塞,知道可以取得结果为止
   Integer result = ft.get();
   System.out.println("计算的结果是:" + result);
  } catch (InterruptedException e) {
   e.printStackTrace();
  } catch (ExecutionException e) {
   e.printStackTrace();
  }
  System.out.println("取得分支线程执行的结果后,主线程可以继续处理其他事项");
 }

}

class CountNum implements Callable {
 private Integer sum;

 public CountNum(Integer sum) {
  this.sum = sum;
 }

 public Object call() throws Exception {
  for (int i = 0; i < 100; i++) {
   sum = sum + i;
  }
  // 休眠5秒钟,观察主线程行为,预期的结果是主线程会继续执行,到要取得FutureTask的结果是等待直至完成。
  Thread.sleep(3000);
  System.out.println("futureTask 执行完成" + System.currentTimeMillis());
  return sum;
 }

}
 


运行的结果是:
futureTask开始执行计算:1280114852250
main 主线程可以做些其他事情:1280114852250
futureTask 执行完成1280114855250
计算的结果是:4950
取得分支线程执行的结果后,主线程可以继续处理其他事项


如果有多个FutureTask要执行批量运算,从而充分的利用多核CPU,可以参考下面的代码:

package com.spell.threads;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.FutureTask;

/**
 * 测试多核时代,充分的利用CPU来运算数据,并且处理返回的结果,学习API专用
 *
 * @author Administrator
 *
 */
public class FutureTaskAndExecutor {

 /**
  * @param args
  */
 public static void main(String[] args) {
  List<FutureTask<Integer>> list = new ArrayList<FutureTask<Integer>>();
  // 创建线程池,线程池的大小和List.size没有啥必然的关系,一般的原则是<=list.size,多出来浪费不好
  ExecutorService exec = Executors.newFixedThreadPool(5);
  for (int i = 10; i < 20; i++) {
   // 创建对象
   FutureTask<Integer> ft = new FutureTask<Integer>(new GetSum(i));
   // 添加到list,方便后面取得结果
   list.add(ft);
   // 一个个提交给线程池,当然也可以一次性的提交给线程池,exec.invokeAll(list);
   exec.submit(ft);
  }

  // 开始统计结果
  Integer total = 0;
  for (FutureTask<Integer> tempFt : list) {
   try {
    total = total + tempFt.get();
   } catch (InterruptedException e) {
    e.printStackTrace();
   } catch (ExecutionException e) {
    e.printStackTrace();
   }
  }

  // 处理完毕,一定要记住关闭线程池,这个不能在统计之前关闭,因为如果线程多的话,执行中的可能被打断
  exec.shutdown();
  System.out.println("多线程计算后的总结果是:" + total);

 }
}
 
/**
 * 这个类很简单,就是统计下简单的加法(从1 到total)
 *
 * @author Administrator
 *
 */
class GetSum implements Callable {
 private Integer total;
 private Integer sum = 0;

 public GetSum(Integer total) {
  this.total = total;
 }

 public Object call() throws Exception {
  for (int i = 1; i < total + 1; i++) {
   sum = sum + i;
  }
  System.out.println(Thread.currentThread().getName() + " sum:" + sum);
  return sum;
 }

}

 

运行的结果是:
pool-1-thread-1 sum:120
pool-1-thread-1 sum:136
pool-1-thread-1 sum:153
pool-1-thread-1 sum:171
pool-1-thread-1 sum:190
pool-1-thread-2 sum:66
pool-1-thread-3 sum:78
pool-1-thread-4 sum:91
pool-1-thread-5 sum:105
多线程计算后的总结果是:1165

分享到:
评论

相关推荐

    Java线程池FutureTask实现原理详解

    Java线程池FutureTask实现原理详解 Java线程池FutureTask实现原理详解是Java多线程编程中的一种重要机制,用于追踪和控制线程池中的任务执行。下面将详细介绍FutureTask的实现原理。 类视图 为了更好地理解...

    Java中Future、FutureTask原理以及与线程池的搭配使用

    Java中的`Future`和`FutureTask`是并发编程中重要的工具,它们允许程序异步执行任务并获取结果。`Future`接口提供了对异步计算结果的访问和控制,而`FutureTask`是`Future`的一个具体实现,它还同时实现了`Runnable`...

    futuretask用法及使用场景介绍

    例如,在一个科学计算应用中,需要对大量数据进行计算,可以使用FutureTask和ExecutorService来实现多任务计算。 三、FutureTask的实现机制 FutureTask的实现机制是通过传入Runnable或者Callable的任务给...

    Java线程超时监控

    在Java编程中,多线程是并发执行任务的重要方式,然而在实际应用中,我们可能会遇到某些线程执行时间过长或死锁的情况,这可能导致系统资源的浪费甚至整体性能下降。因此,对线程进行超时监控是必要的,以确保程序的...

    简谈java并发FutureTask的实现

    Java并发编程中,`FutureTask`是一个非常关键的组件,它结合了`Runnable`和`Future`接口的能力,使得我们可以在异步执行的任务完成后获取其结果。`FutureTask`不仅是一个可取消的任务,还能报告其执行状态。在这个...

    比较java中Future与FutureTask之间的关系

    在Java中,Future和FutureTask都是用于获取线程执行的返回结果,但是它们之间存在一些差异和关联。本文将详细介绍Future和FutureTask的关系、使用和分析。 一、Future介绍 Future位于java.util.concurrent包下,是...

    Java FutureTask类使用案例解析

    Java FutureTask类使用案例解析 Java FutureTask类是一种异步计算的工具,用于执行长时间的任务并获取结果。它实现了Runnable和Future接口,既可以作为一个Runnable对象提交给Executor执行,也可以作为一个Future...

    Java中的Runnable,Callable,Future,FutureTask的比较

    Java中的Runnable、Callable、Future和FutureTask是Java多线程编程中的核心概念,它们各自扮演着不同的角色,共同协作以实现并发任务的管理和执行。 1. **Runnable**: Runnable是最基本的多线程接口,它只有一个`...

    Android(Java)之多线程结果返回——Future 、FutureTask、Callable、Runnable

    `Future`、`FutureTask`、`Callable`和`Runnable`是Java并发编程中的核心接口和类,它们在Android开发中同样有着广泛的应用。下面将详细介绍这些概念以及它们如何协同工作。 1. `Runnable`: 这是Java中最基础的多...

    FutureTask学习

    `FutureTask`是Java并发编程中的一个重要组件,它位于`java.util.concurrent`包下,是`Executor`框架的一部分。这个类结合了`Runnable`或`Callable`接口的特性,并提供了异步执行的能力,同时允许你在任务完成后获取...

    spring线程池ThreadPoolExecutor配置以及FutureTask的使用

    在Java的多线程编程中,Spring框架提供了一种便捷的方式来管理和配置线程池,这就是`ThreadPoolTaskExecutor`。这个类是Spring对Java内置的`java.util.concurrent.ThreadPoolExecutor`的封装,允许开发者在Spring...

    并发编程_应用1

    本文将深入探讨如何通过多线程充分利用CPU资源,以及在实际应用中如何进行并行计算的选择和优化。 首先,多线程的目的是让多个任务能够同时执行,从而提高计算机的处理能力。在Java中,可以使用`Thread`类或`...

    揭密FutureTask.docx

    在Java并发编程中,FutureTask扮演着至关重要的角色,它是实现异步计算的关键组件。本文将深入探讨FutureTask的原理和用法,帮助开发者更好地理解和利用这个强大的工具。 一、Future接口与FutureTask概述 Future...

    java并发编程内部分享PPT

    Java并发编程是Java开发中的重要领域,特别是在多核处理器和分布式系统中,高效地利用并发可以极大地提升程序的性能和响应速度。这份“java并发编程内部分享PPT”显然是一个深入探讨这一主题的资料,旨在帮助开发者...

    Java并发编程常识-梁飞.rar

    Java并发编程是Java开发中的重要领域,特别是在多核处理器和分布式系统中,高效地利用并发可以极大地提升程序的性能和响应速度。阿里大牛梁飞编写的《Java并发编程常识》PPT,深入浅出地讲解了这个主题,对开发者来...

    Java并发工具包

    Java并发工具包是Java平台中的一个关键特性,它位于`java....理解并熟练使用这些工具,能够显著提升Java程序在多核环境下的性能,降低并发编程的复杂性和出错风险。学习和掌握这个工具包是Java开发者的必备技能之一。

    Java 多线程与并发(17-26)-JUC线程池- FutureTask详解.pdf

    3. **资源管理**:利用`FutureTask`的`cancel`方法,可以在特定条件下提前结束任务,节省系统资源。 #### 七、总结 `FutureTask`是Java并发编程中一个非常重要的工具,它不仅可以用于封装任务并异步执行,还能方便...

    我的java并发PPT

    在Java中,并发处理是提升程序效率和充分利用多核处理器能力的重要手段。 在PPT中,可能涵盖了以下几个核心概念: 1. **线程**: Java中的`Thread`类是线程的基类,通过创建Thread对象并调用其`start()`方法来启动...

    高清完整版 Mastering Concurrency Programming with Java

    这种技术可以显著提高系统的性能和响应能力,尤其是在多核处理器普及的今天。Java 作为一种广泛使用的编程语言,提供了丰富的并发编程支持。 #### 二、Java 并发编程框架概述 在 Java 中,处理并发主要依赖于 Java...

    java并发编程

    并发编程能够充分利用多核处理器的计算能力,提高应用程序的响应速度和整体性能。《Java编程并发实战》这本书是学习这一主题的重要参考资料。 在Java中,线程是并发的基础。Java通过内置的`Thread`类和`Runnable`...

Global site tag (gtag.js) - Google Analytics