2015-03-03 36 views
3

function2()通過函數2()獲得什麼利潤(除了兩個GET查詢執行時的小並行性)?在我看來,控制器線程在兩種情況下都不被阻塞,但是在等待結果時必須阻止其中一個後臺線程。更好的例子是,當我們查看function3()時,我們看到databaseDao線程被阻塞直到操作完成(在使用JPA的dao內部)。發揮框架,承諾,非阻塞線程編程

public static F.Promise<Result> function1() { 
    final F.Promise<WSResponse> twitterPromise = WS.url("http://www.twitter.com").get(); 
    final F.Promise<WSResponse> typesafePromise = WS.url("http://www.typesafe.com").get(); 

    return twitterPromise.flatMap((twitter) -> typesafePromise.map((typesafe) -> ok(twitter.getBody() + typesafe.getBody()))); 
} 

public static F.Promise<Result> function2() { 
    F.Promise<String> promise = F.Promise.promise(() -> { 
     HttpClient client = HttpClientBuilder.create().build(); 
     HttpGet request1 = new HttpGet("http://www.twitter.com"); 
     HttpGet request2 = new HttpGet("http://www.typesafe.com"); 

     HttpResponse response = client.execute(request1); 
     HttpResponse response2 = client.execute(request2); 

     // result is not important 
     return response.toString() + response2.toString(); 
    }); 

    return promise.map(Results::ok); 
} 

public static F.Promise<Result> function3() { 
    F.Promise<String> promise = F.Promise.promise(() -> databaseDao.longRunningOperation()); 

    return promise.map(Results::ok); 
} 

如果函數阻塞我們的後臺線程池消失得很快。那麼非盈利性的框架和Spring框架和tomcat的承諾呢?

編輯:

public static F.Promise<Result> function4() { 
    F.Promise<String> promise = F.Promise.promise(() -> { 
     HttpClient client = HttpClientBuilder.create().build(); 
     HttpGet request1 = new HttpGet("http://www.twitter.com"); 
     HttpResponse response = client.execute(request1); 

     return response.toString(); 
    }); 

    F.Promise<String> promise2 = F.Promise.promise(() -> { 
     HttpClient client = HttpClientBuilder.create().build(); 
     HttpGet request2 = new HttpGet("http://www.typesafe.com"); 
     HttpResponse response2 = client.execute(request2); 
     return response2.toString(); 
    }); 

    return promise.flatMap(p1 -> promise2.map(p2 -> ok(p1 + p2))); 
} 

上面的函數阻止兩個線程,因此它比功能1更糟?但執行時間可以相當。例如,如果promise1需要5秒,並且promise2需要4秒,結果會在5秒內出現?

+0

在你的第一個例子中,如果twitter req。需要5秒鐘和類型安全需求。需要4秒鐘,你會在5秒內得到你的結果。在第二個功能中,需要9秒。另外對於我所知道的JDBC而言,如果你使用Play,Spring或者???,那麼它並不重要,它會阻止某處 – Salem 2015-03-03 15:27:54

回答

2

function2()相對於function2()有什麼好處(除了執行兩個GET查詢時的小並行性)?

這不僅僅是並行性。玩WS是基於AsyncHttpClient構建的,它是一個非阻塞API。在function2它看起來像你正在使用Apache HttpClient,這是一個阻塞API。並行性有所幫助。至於@Salem已經表示,function1將只會提出最長的請求,而function2將只要這兩個請求每次都會花費時間。

在我看來控制器線程被阻塞非在這兩種情況下,...

誠然,我們不會阻止播放機的內部,只要Promise穿梭到另一個ExecutionContext

...但是在等待結果時必須阻止後臺線程之一。

不正確。由於function1僅對WS API執行異步調用,因此它不會阻止任何線程等待響應。 function2可能不會阻塞負責控制器功能的線程,但它必須阻止某個地方。這並不是說將它包裝在Promise中是一個壞主意 - 如果它必須阻止,它可能會在其他地方做到。

...看看function3()我們看到databaseDao線程被阻塞直到操作完成(使用JPA內部dao)。

事實上,大多數數據庫驅動程序都會阻塞,除了嘗試不太流行的異步驅動程序之外,沒有任何辦法可以解決這個問題。 function2function3在行爲上比function1function2更接近。 function真的屬於它自己的一類。

如果函數阻塞我們的後臺線程池消失得很快。

是的,但大多數時候我們必須阻止某處,如果您有使用異步API的選擇,那麼很好。例如,由於上面解釋的原因,我總是會使用function1而不是function2。但是對於數據庫調用,我使用阻塞API,因爲在數據庫中的應用程序中,如果我的數據庫已經超載了查詢,那麼保存一些應用程序線程並不能真正幫助我。

上面的函數[function4]阻塞兩個線程,所以它比function1差?但執行時間可以相當。例如,如果promise1需要5秒,並且promise2需要4秒,結果會在5秒內出現?

function4更糟糕的是它比function1阻塞更多。是否影響您的應用程序的性能立即取決於您是否碰到線程數。但我沒有看到任何理由選擇function4而不是function1function4可以在與function1,提供的相當的時間內完成,它具有必要的線程來完成。如果池中只有一個線程可用,那麼第二個許諾可能需要等待第一個完成才能執行。在function1,這不會發生。

+0

你可以看一下編輯部分嗎?並回答我。謝謝 :) – user2860204 2015-03-04 12:40:25