美文网首页
Future设计模式

Future设计模式

作者: 得力小泡泡 | 来源:发表于2021-01-18 19:55 被阅读0次

1、Future前言

Future设计模式从本质上是用来解决的根本的问题在于可以让一个任务在异步执行,而任务执行完之后我们可以在未来的某一个时间点上去获取到这个任务执行的结果,不管这个任务是执行失败或成功

举个例子
比如我们要完成一件任务,正常情况是要等到这个任务执行完之后才能拿到任务执行的结果【单线程顺序执行逻辑】,而如果使用Future模式之后,则执行任务可以交由别的线程来执行,而我们可继续往下执行自己的事件,当在未来的某个时间点又能拿到这个任务的结果,其实也就是并行的方式。可能有的人说这不就是线程嘛,是的,但是普通的线程我们要等其执行完不得使用join()么,但是它会阻塞我们的继续往下执行。

2、Future官方文档

一个Future代表了一个异步计算的结果,它提供了很多方法用来检查此计算是否完成,或者等待它的完成,以及获取计算的结果。只有当计算结果后才可以使用get()方法来获取结果,必要时会进行阻塞直到任务执行结束。可以通过cancel()方法对其任务进行取消,此外还提供了其他方法来确定任务是正常完成还是说被取消了。

核心方法
  • 1、boolean cancel(boolean mayInterruptIfRunning)
    尝试取消此任务
  • 2、boolean isCancelled()
    如果此任务在正常完成之前被取消,则返回 true 。
  • 3、boolean isDone()
    是否任务执行完了
  • 4、V get()
    获取任务执行结果,如果任务没有完成,这个方法则会一直等待,没有超时机制
  • 5、V get(long timeout, TimeUnit unit)
    获取任务执行结果,如果任务没有完成,这个方法则会一直等待,直到超过限定时间,超过限定时间则会抛出异常

3、FutureTask

对于Future而言它是一个接口,要使用还得用具体实现类,FutureTask就是Future的一个具体实现类之一,比较常见,观察FutureTask实现的接口,就知道它有什么样的能力

image.png
瞅一下RunnableFuture呗:
image.png
接下来再来看一下FutureTask的重要方法:
两种构造方法
方法1
    public FutureTask(Callable<V> callable) {
        if (callable == null)
            throw new NullPointerException();
        this.callable = callable;
        this.state = NEW;       // ensure visibility of callable
    }

方法2

    public FutureTask(Runnable runnable, V result) {
        this.callable = Executors.callable(runnable, result);
        this.state = NEW;       // ensure visibility of callable
    }

对于上面两个构造的使用场景其实也很好理解

  • 当我们需要有返回结果当然就使用Callable的构造
  • 当我们想要执行一个任务但是不需要得到返回结果,那么用Runnable的构造,其中方法二中传入Runnable方法最终会转换为使用Callable的构造方法

看一下Callable接口的定义


image.png
举例子观察FutureTask的使用
package com.concurrency2;

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

public class MyTest5 {
    public static void main(String[] args) {
        Callable<Integer> callable = () -> {
            System.out.println("子任务执行中");

            try {
                Thread.sleep(3000);
            } catch (Exception e) {
                e.printStackTrace();
            }

            int randomNumber = new Random().nextInt(500);

            System.out.println("子任务执行中");

            return randomNumber;
        };

        FutureTask<Integer> futureTask = new FutureTask<Integer>(callable);

        new Thread(futureTask).start();

        System.out.println("主任务执行中");

        try {
            System.out.println("task result:" + futureTask.get());
        } catch (Exception e) {
            e.printStackTrace();
        }

        System.out.println("主任务已完成");
    }
}

输出

主任务执行中
子任务执行中
子任务执行中
task result:177
主任务已完成

分析:
new Thread(futureTask).start();执行的是开辟一个子任务,执行的是callable的内容并要求返回Integer类型的结果,而callable的内容作为变量传进FutureTask中。因此现在就有两个线程一起执行,一个是主任务线程,一个是子任务线程,而后面主任务线程需要拿到子任务线程执行完的结果,因此一定要执行完futureTask.get()方法时,主任务线程才会继续执行下去,否则会一直进入等待状态(如果get()方法是带时间参数的方法,若超过的指定的时间则主任务线程会抛出异常,而子任务线程不会抛出异常,因为和子任务线程无关)


Future模式,它有一个最大的缺点就是调用get()方法来获取其任务的结果时会阻塞,还有一个CompletableFuture的实现类,弥补Future的不足,使得任务执行时和结果获取时都不阻塞,这里不做详细总结,具体看这里https://mp.weixin.qq.com/s/cu09f_LD4SlywZMTCBeokA

相关文章

  • Java8 CompletableFuture指北

    一、JAVA 异步处理的演变 1.1 Future JDK 5引入了Future模式。Future模式是多线程设计...

  • Future

    Future模式 概念 ```Future模式是多线程设计常用的一种设计模式,类似商品订单。商品下单后,会立即得到...

  • 多线程Future设计模式的两种用法

    多线程Future设计模式 Future接口定义: Future接口的实现类: 封装任务的FutureTask接口...

  • Future设计模式

    一、什么是Future模式:Future设计模式是Java多线程开发常用设计模式。一句话,将客户端请求的处理过程从...

  • Future设计模式

    1. 前言 在讲future模式之前,需要先理解什么是同步,什么是异步? 同步:当任务a依赖于任务b的执行时,必须...

  • Future设计模式

    1、Future前言 Future设计模式从本质上是用来解决的根本的问题在于可以让一个任务在异步执行,而任务执行完...

  • 并行设计模式(一)-- Future模式

    Java多线程编程中,常用的多线程设计模式包括:Future模式、Master-Worker模式、Guarded ...

  • concurrent中Future真实例子分享

    Future是非常常用的多线程设计模式,因此在JDK中内置了Future模式的实现。这些类在java.util.c...

  • Java多线程 - Future模式

    什么是Future模式 Future模式是多线程开发中非常常见的一种设计模式。它的核心思想是异步调用。当我们需要调...

  • Future三重奏第三章:FutureTask中一些知识点的总结

    Future系列文章 Future三重奏第一章:Future设计模式及代码示例Future三重奏第二章:Futur...

网友评论

      本文标题:Future设计模式

      本文链接:https://www.haomeiwen.com/subject/fsvaaktx.html