日日操夜夜添-日日操影院-日日草夜夜操-日日干干-精品一区二区三区波多野结衣-精品一区二区三区高清免费不卡

公告:魔扣目錄網(wǎng)為廣大站長提供免費收錄網(wǎng)站服務(wù),提交前請做好本站友鏈:【 網(wǎng)站目錄:http://www.ylptlb.cn 】, 免友鏈快審服務(wù)(50元/站),

點擊這里在線咨詢客服
新站提交
  • 網(wǎng)站:51998
  • 待審:31
  • 小程序:12
  • 文章:1030137
  • 會員:747


 

憑據(jù)管理

在日常生活中,我們經(jīng)常會遇到一種情況,就是在我們提出需求之后,由于服務(wù)者還沒有準(zhǔn)備好對應(yīng)的實物交付給我們的時候,就會先給我們一張憑據(jù),等到雙方約定的時間到了之后,我們帶著這個憑據(jù)就可以去獲取到我們想要的東西。例如在一個蛋糕店里我們定了一個蛋糕,店長給了我們一個憑據(jù),然后在約定的時間我們?nèi)サ案獾曛腥∽呶覀兌ǖ牡案狻_@樣我們不需要在店里等待,而是去完成我們的其他工作。

在程序開發(fā)中假設(shè)有一個任務(wù)執(zhí)行的時間比較長,通常需要我們等待這個任務(wù)完成之后才能進行后續(xù)的任務(wù),這個時候服務(wù)的調(diào)用者就會一直等待。而我們利用上面的介紹的憑據(jù)的方式就完全可以解決調(diào)用者等待的問題。也就是JAVA中常說的Future模式。下面我們就來看看關(guān)于Java中的Future模式。

Future設(shè)計模式

Future設(shè)計模式是從JDK1.5開始出現(xiàn)的,在我們實現(xiàn)多線程操作的時候有常用的兩種方式,一種是實現(xiàn)Runnbale接口,一種是繼承Thread類,而我們不是太常用的一種方式就是Call接口的方式,這種方式就是類似于Future模式。其實現(xiàn)類圖如下。


 

下面我們就來看看Future設(shè)計模式的具體實現(xiàn)方式。

接口邏輯定義

Future接口

根據(jù)之前的分析我們的票據(jù)應(yīng)當(dāng)具有兩個功能,一個功能是可以通過它獲取到我們想要的結(jié)果,另一個功能就是通過它我們可以知道我們想要的蛋糕是否制作完成。如下所示。

public interface Future {// 用于返回計算之后的結(jié)果T get() throws InterruptedException;// 用于判斷任務(wù)是否正常執(zhí)行boolean done();

FutureService接口

FutureService 的主要作用就是任務(wù)的提交,而提交任務(wù)的方式有兩種,一種是不需要返回值的,一種是需要返回值的。代碼如下。

public interface FutureService {// 提交不需要進行返回的任務(wù)的時候 Future的get方法返回為空Future submit(Runnable runnable);// 提交需要返回值的任務(wù)的時候 Future的get方法就是獲取到返回值Future submit(Tasktask,IN input);// 靜態(tài)方法獲取到實現(xiàn)實例對象static FutureService newServcie(){return new FutureServiceImpl<>();

Task接口

有了票據(jù),有了服務(wù)人員,接下來就是需要有我們需要完成的任務(wù)是什么,而Task就是用來提供給調(diào)用者實現(xiàn)計算邏輯的任務(wù)。可以接受一個參數(shù)并且返回最后的結(jié)果。有點類似于Callable接口

@FunctionalInterfacepublic interface Task {//給定一個參數(shù)經(jīng)過計算之后得到一個結(jié)果OUT get(IN input);Future程序?qū)崿F(xiàn)

Future接口實現(xiàn)

會發(fā)現(xiàn)這個接口實現(xiàn)除了實現(xiàn)Future接口的兩個方法之外還增加了一個finish的方法,用來完成任務(wù)通知操作。

public class FutureTask implements Future {// 返回結(jié)果private T result;//任務(wù)是否完成private boolean isDone = false;// 對象鎖private final Object LOCK = new Object();@Overridepublic T get() throws InterruptedException {synchronized (LOCK){//當(dāng)任務(wù)還沒有完成的時候,調(diào)用get方法會被掛起進入阻塞等待while (!isDone){LOCK.wait();// 返回計算結(jié)果return result;protected void finish(T result){synchronized (LOCK){//balking 設(shè)計模式if (isDone){return;// 計算完成,為result指定結(jié)果,并且將isDone設(shè)置為true,同時喚起等待中的線程this.result = result;this.isDone = true;LOCK.notifyAll();@Overridepublic boolean done() {return isDone;

在FutureTask中使用了線程間的通信wait和notifyAll,當(dāng)任務(wù)沒有完成之前通過get方法獲取接口,調(diào)用方會進入到阻塞狀態(tài),直到任務(wù)完成之后收到線程喚醒,finish方法接收到任務(wù)完成的通知,然后喚醒因為調(diào)用了get方法而進入阻塞的線程。

FutureService實現(xiàn)

public class FutureServiceImpl implements FutureService {private final static String FUTURE_THREAD_PREFIX = "FUTURE-";private final AtomicInteger nextCounter = new AtomicInteger(0);private String getNextName(){return FUTURE_THREAD_PREFIX+nextCounter.getAndIncrement();@Overridepublic Future submit(Runnable runnable) {final FutureTask future = new FutureTask<>();new Thread(()->{runnable.run();// 任務(wù)執(zhí)行結(jié)束之后將null作為參數(shù)返回future.finish(null);},getNextName()).start();return future;@Overridepublic Future submit(Task task, IN input) {final FutureTask future = new FutureTask<>();new Thread(()->{OUT result = task.get(input);// 任務(wù)執(zhí)行結(jié)束之后,將真實的結(jié)果通過finish的方式傳遞給futurefuture.finish(result);},getNextName()).start();return future;Future設(shè)計模式測試

這里我們提交一個沒有返回值的任務(wù),代碼如下,

public class FutureTest {public static void main(String[] args) throws InterruptedException {FutureService service = FutureService.newServcie();Future future = service.submit(()->{try {TimeUnit.SECONDS.sleep(10);} catch (InterruptedException e) {e.printStackTrace();System.out.println("任務(wù)完成!");future.get();

提交一個有返回值的任務(wù)

public class FutureTest {public static void main(String[] args) throws InterruptedException {FutureService service = FutureService.newServcie();Future future = service.submit(input->{try {TimeUnit.SECONDS.sleep(10);} catch (InterruptedException e) {e.printStackTrace();return input.length();},"Hello");System.out.println(future.get());升級獲取結(jié)果的方法

從上面兩個測試的返回結(jié)果來看,如果我們調(diào)用了future的get方法,那么我們的程序就會進入到阻塞的狀態(tài),這個操作與我們的預(yù)期不太相符合,這個也是整個的Future模式一直存在的問題。那么我們?nèi)绾稳ジ倪M這個獲取get方法等待的問題呢?這就引入了一個Callback的機制。代碼如下

@Overridepublic Future submit(Task task, IN input, Callback callback) {final FutureTask future = new FutureTask<>();new Thread(()->{OUT result = task.get(input);// 任務(wù)執(zhí)行結(jié)束之后,將真實的結(jié)果通過finish的方式傳遞給futurefuture.finish(result);if (null!=callback){callback.call(result);},getNextName()).start();return future;

測試效果,會發(fā)現(xiàn)我們課可以不使用get方法就可以完成執(zhí)行結(jié)果的獲取。

public class FutureTest {public static void main(String[] args) throws InterruptedException {FutureService service = FutureService.newServcie();service.submit(input->{try {TimeUnit.SECONDS.sleep(10);} catch (InterruptedException e) {e.printStackTrace();return input.length();},"Hello",System.out::println);總結(jié)

在之前的分享中很多的地方我們都提到了Future設(shè)計模式,通過這篇文章我們也進一步的了解了關(guān)于Future設(shè)計模式的思想。其核心思想就是模擬了一個憑據(jù)場景,通過這種方式來實現(xiàn)對CPU的高效利用。當(dāng)然這里我們給出的只是一個基礎(chǔ)演示版本,其中的存在的問題還有很多,有興趣的讀者可以自己思考相關(guān)內(nèi)容的優(yōu)化。

分享到:
標(biāo)簽:Future
用戶無頭像

網(wǎng)友整理

注冊時間:

網(wǎng)站:5 個   小程序:0 個  文章:12 篇

  • 51998

    網(wǎng)站

  • 12

    小程序

  • 1030137

    文章

  • 747

    會員

趕快注冊賬號,推廣您的網(wǎng)站吧!
最新入駐小程序

數(shù)獨大挑戰(zhàn)2018-06-03

數(shù)獨一種數(shù)學(xué)游戲,玩家需要根據(jù)9

答題星2018-06-03

您可以通過答題星輕松地創(chuàng)建試卷

全階人生考試2018-06-03

各種考試題,題庫,初中,高中,大學(xué)四六

運動步數(shù)有氧達人2018-06-03

記錄運動步數(shù),積累氧氣值。還可偷

每日養(yǎng)生app2018-06-03

每日養(yǎng)生,天天健康

體育訓(xùn)練成績評定2018-06-03

通用課目體育訓(xùn)練成績評定