Java深入学习(4):Future模式
程序员文章站
2022-07-02 12:59:38
Future模式: 其实相当于是前端的Ajax 比如我们使用多线程下载文件时候,每一个线程都会发送HTTP请求资源。而我如何知道,文件下载完毕呢? 也就是说,主线程如何获得子线程的执行结果呢? 创建多线程中的实现runnable接口方式和继承thread类,然后start方法都是直接执行代码的,无法 ......
future模式:
其实相当于是前端的ajax
比如我们使用多线程下载文件时候,每一个线程都会发送http请求资源。而我如何知道,文件下载完毕呢?
也就是说,主线程如何获得子线程的执行结果呢?
创建多线程中的实现runnable接口方式和继承thread类,然后start方法都是直接执行代码的,无法知道执行的结果(主线程无法知道进度)。
这里要说的是新方式:使用callable接口和future模式
public class callabletest { public static void main(string[] args) throws exception { executorservice newcachedthreadpool = executors.newcachedthreadpool(); future<string> submit = newcachedthreadpool.submit(new taskcallable()); system.out.println("主线程运行"); string result = submit.get(); system.out.println(result); } } class taskcallable implements callable { @override public string call() throws exception { system.out.println("开始执行任务"); thread.sleep(3000); system.out.println("执行任务结束"); return "success"; } }
打印:
主线程运行 开始执行任务 执行任务结束 success
future模式核心:去除了主函数的等待时间,并使得原本需要等待的时间段可以用于处理其他业务逻辑
future模式实例:对于多线程,如果线程a要等待线程b的结果,那么线程a没必要等待b,直到b有结果,可以先拿到一个未来的future,等到b有结果时再取真实的结果
自己实现future模式:
/** * 公共data数据结果 */ public abstract class data { /** * 返回线程的执行结果 * @return string */ public abstract string getrequest(); }
/** * 获取真实数据 */ public class realdata extends data { private string result; realdata(string data) { system.out.println("正在使用data->" + data + " 进行网络请求"); try { thread.sleep(3000); } catch (exception e) { e.printstacktrace(); } system.out.println("操作执行完毕"); this.result = "success"; } @override public string getrequest() { return result; } }
/** * 当有线程要获取realdata的时候 * 程序会被阻塞 * 等到realdata被注入才会使用getrequest方法 */ public class futuredata extends data { private boolean flag = false; private realdata realdata; /** * 读取data数据 */ public synchronized void setrealdata(realdata realdata) { //如果获取到数据直接返回 if (flag) { return; } //如果没有获取到数据 this.realdata = realdata; flag = true; notify(); } @override public synchronized string getrequest() { while (!flag) { try { wait(); } catch (exception e) { e.printstacktrace(); } } return realdata.getrequest(); } }
public class futureclient { public data submit(string requestdata){ futuredata futuredata = new futuredata(); new thread(new runnable() { @override public void run() { realdata realdata = new realdata(requestdata); futuredata.setrealdata(realdata); } }).start(); return futuredata; } }
测试类:
public class main { public static void main(string[] args) { futureclient futureclient = new futureclient(); data request = futureclient.submit("666"); system.out.println("主线程数据发送成功"); system.out.println("主线程执行其他任务"); string result = request.getrequest(); system.out.println(result); } }
打印如下:
主线程数据发送成功 主线程执行其他任务 正在使用data->666 进行网络请求 操作执行完毕 success