栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

【学习】线程池:获取任务执行结果get与取消任务cancel方法

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

【学习】线程池:获取任务执行结果get与取消任务cancel方法

线程池:系列三

阻塞式和定时式那种获取任务方式更好?

Future获取结果的方式有两种

一个是无参的get方法,另一个是有参的get方法 总结 取消任务的cancel方法的一些困惑

cancel(boolean) 取消任务

true:表示尝试中断正在执行任务的线程(只对执行中的任务有意义)

取消正在执行的任务 false:则相反

取消未执行任务取消已完成任务 总结 参考地址

阻塞式和定时式那种获取任务方式更好? Future获取结果的方式有两种

一个是无参的get方法,

它是阻塞式的,获取结果会一直等到结果输出。案例如下:先创建任务类

import java.util.concurrent.Callable;


public class ResultTask implements Callable {

    public Integer call() throws Exception {
        return 1+1;
    }
}

然后创建单个线程池获取任务结果

import com.naidou.threadPool.tp04.ResultTask;

import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;


public class ThreadPool05 {

    public static void main(String[] args) {
        // 创建任务
        com.naidou.threadPool.tp04.ResultTask task = new ResultTask();
        // 创建单个线程的线程池
        ExecutorService threadPool = Executors.newSingleThreadExecutor();
        // 提交任务
        Future future = threadPool.submit(task);
        try {
            // 获取任务执行结果
            Integer result = future.get();
            // 输出任务执行结果
            System.out.println(result);
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        } finally {
            // 关闭线程池
            threadPool.shutdown();
        }

    }

}

输出结果:程序正常输出
另一个是有参的get方法

我们可以设置获取结果的超时时间,如果大于超时时间,那么程序会抛出TimeoutException异常
案例如下:先创建任务类,设置线程休眠时间为3秒

import java.util.concurrent.Callable;
import java.util.concurrent.TimeUnit;


public class ResultTask01 implements Callable {

    public Integer call() throws Exception {
        // 使当前线程休眠3秒钟
        TimeUnit.SECONDS.sleep(3);
        return 1+1;
    }
}

然后创建单个线程获取任务,先设置获取结果超时时间为1秒

import java.util.concurrent.*;


public class ThreadPool051 {

    public static void main(String[] args) {
        // 创建任务
        ResultTask01 task = new ResultTask01();
        // 创建单个线程的线程池
        ExecutorService threadPool = Executors.newSingleThreadExecutor();
        // 提交任务
        Future future = threadPool.submit(task);
        try {
            // 获取任务执行结果
            Integer result = future.get(1,TimeUnit.SECONDS);
            // 输出任务执行结果
            System.out.println(result);
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        } catch (TimeoutException e) {
            e.printStackTrace();
        } finally {
            // 关闭线程池
            threadPool.shutdown();
        }

    }

}

输出结果:抛出超时异常,符合预期
然后设置超时时间为5秒

// 获取任务执行结果
            Integer result = future.get(5,TimeUnit.SECONDS);

输出结果:3秒后程序正常输出,符合预期
总结

两种写法都可以,依据不同业务视情况而定,一般用无参方法比较多。 取消任务的cancel方法的一些困惑 cancel(boolean) 取消任务 true:表示尝试中断正在执行任务的线程(只对执行中的任务有意义) 取消正在执行的任务

创建任务类

import java.util.concurrent.Callable;


public class ResultTask042 implements Callable {

    public Integer call() throws Exception {
        // 计数器
        int i = 0;
        // 当线程没被中断时
        while (!Thread.interrupted()){
            // 递增i
            i++;
        }
        // 输出i
        System.out.println("i的值:"+i);
        // 返回1+1的值
        return 1+1;
    }
}

线程取消正在执行任务

import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;


public class ThreadPool042 {

    public static void main(String[] args) {
        // 创建任务
        ResultTask task = new ResultTask();
        // 创建单个线程的线程池
        ExecutorService threadPool = Executors.newSingleThreadExecutor();
        // 提交任务
        Future future = threadPool.submit(task);
        System.out.println("任务是否完成:" + future.isDone());
        // 取消任务 调用interrupt打断
        boolean cancel = future.cancel(true);
        System.out.println("任务是否取消成功:" + cancel);
        System.out.println("任务是否取消:" + future.isCancelled());
        try {
            // 获取任务执行结果
            Integer result = future.get();
            // 输出任务执行结果
            System.out.println(result);
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        } finally {
            // 关闭线程池
            threadPool.shutdown();
        }
    }
}

输出结果:任务取消成功,并引发CancellationException 异常
false:则相反 取消未执行任务

创建任务类

import java.util.concurrent.Callable;


public class ResultTask implements Callable {

    public Integer call() throws Exception {
        return 1+1;
    }
}

取消未执行任务

import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;


public class ThreadPool04 {

    public static void main(String[] args) {
        // 创建任务
        ResultTask task = new ResultTask();
        // 创建单个线程的线程池
        ExecutorService threadPool = Executors.newSingleThreadExecutor();
        // 提交任务
        Future future1 = threadPool.submit(task);
        Future future2 = threadPool.submit(task);
        // 取消任务 调用interrupt打断 取消未执行任务
        boolean cancel = future2.cancel(false);
        System.out.println("任务是否取消成功:" + cancel);
        System.out.println("任务是否取消:" + future2.isCancelled());
        try {
            // 获取任务执行结果
            Integer result = future2.get();
            // 输出任务执行结果
            System.out.println(result);
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        } finally {
            // 关闭线程池
            threadPool.shutdown();
        }

    }

输出结果:任务取消成功,获取结果引发CancellationException 异常
取消已完成任务

尝试取消已完成任务

import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;


public class ThreadPool041 {

    public static void main(String[] args) {
        // 创建任务
        ResultTask task = new ResultTask();
        // 创建单个线程的线程池
        ExecutorService threadPool = Executors.newSingleThreadExecutor();
        // 提交任务
        Future future = threadPool.submit(task);
        try {
            // 获取任务执行结果
            Integer result = future.get();
            // 输出任务执行结果
            System.out.println(result);
            // 取消任务 调用interrupt打断 取消未执行任务
            boolean cancel = future.cancel(false);
            System.out.println("任务是否取消成功:" + cancel);
            System.out.println("任务是否取消:" + future.isCancelled());
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        } finally {
            // 关闭线程池
            threadPool.shutdown();
        }

    }

}

输出结果:已完成任务无法取消
总结

参考地址

线程池视频讲解05,06

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/737582.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号