■ Future パターン
* 将来実行できる状態になるまで待つ * 処理の実行担当者は、処理が渡されると別スレッド上で処理を開始して、 メインスレッドには即座にFutureオブジェクトを返すこと * 現在はまだ結果を取得できないが、将来のある時点で取得することになる
補足:JavaScript/TypeScriptの場合
* JavaScript/TypeScriptの場合、Promiseオブジェクトに当たる。
非同期処理 ~ async/await, Promise ~
https://dk521123.hatenablog.com/entry/2021/01/16/202822
■ サンプル
http://www.hyuki.com/dp/dpinfo.html#Future
を参考に、Future パターンを理解するためのプログラムを組む。 (実際には、java.util.concurrent を使った方がいいらしいので、あくまで理解のため)
IDrawing.java
// インターフェイスを用意する public interface IDrawing { public abstract void draw(String content); }
FutureDrawer.java
// 用意したインターフェイスを継承する public class FutureDrawer implements IDrawing { private IDrawing drawer; public synchronized void draw(String content) { while (this.drawer == null) { try { System.out.println("\tIn FutureDrawer: wait"); wait(); } catch (InterruptedException e) { } } System.out.println("\tIn FutureDrawer : drawing start."); this.drawer.draw(content); } public synchronized void setPrinter(IDrawing drawer) { this.drawer = drawer; notifyAll(); } }
RealDrawer.java
// 用意したインターフェイスをこっちも継承する public class RealDrawer implements IDrawing { public void draw(String content) { System.out.println("\tRealDrawer draws \"" + content + "\""); } }
DrawManager.java
import java.util.Random; public class DrawManager extends Thread { private FutureDrawer drawer; public DrawManager() { this.drawer = new FutureDrawer(); } public void run() { System.out.println(Thread.currentThread().getName() + " is sleeping."); try { this.doHeavyJob(); } catch (InterruptedException e) { } System.out.println(Thread.currentThread().getName() + " sets a RealDrawera."); this.drawer.setPrinter(new RealDrawer()); } public void requestDrawing(String content) { this.drawer.draw(content); } private void doHeavyJob() throws InterruptedException { Random random = new Random(); Thread.sleep(random.nextInt(10000)); } }
Main.java
public class Main { public static void main(String[] args) { DrawManager drawManager = new DrawManager(); drawManager.start(); System.out.println( Thread.currentThread().getName() + " is drawing..."); drawManager.requestDrawing("Hello Mike [1]."); drawManager.requestDrawing("Hello Tom [2]."); drawManager.requestDrawing("Hello World [3]."); } }
出力
Thread-0 is sleeping. main is drawing... In FutureDrawer: wait Thread-0 sets a RealDrawera. In FutureDrawer : drawing start. RealDrawer draws "Hello Mike [1]." In FutureDrawer : drawing start. RealDrawer draws "Hello Tom [2]." In FutureDrawer : drawing start. RealDrawer draws "Hello World [3]."
■ 補足
* Future インターフェースがJava標準で用意されている
http://www.techscore.com/tech/Java/JavaSE/Thread/8-3/
参考文献
http://www.hyuki.com/dp/dpinfo.html#Future
http://team-pag.interprism.co.jp/member/okazawa/blog/?p=704
関連記事
非同期処理 ~ async/await, Promise ~
https://dk521123.hatenablog.com/entry/2021/01/16/202822
Python ~ 非同期 / concurrent.futures ~
https://dk521123.hatenablog.com/entry/2023/04/19/232949
Scala ~ 非同期 / Future ~
https://dk521123.hatenablog.com/entry/2023/04/30/000000