Weitere ähnliche Inhalte Ähnlich wie 使用 Java 上的 future/promise API (20) 使用 Java 上的 future/promise API3. About me
• Koji Lin
• @kojilin
• LINE Fukuoka, Japan
• 之前在 Cubie Inc.
• Android & iOS & 一些 Server side
5. 什麼是非同步
• Asynchronous
• Not synchronous, or not
guaranteed to happen in the order
in which it appears in the code
from Playframework: Async, Reactive, Threads, Futures, ExecutionContexts
https://gist.github.com/sadache/4714280
6. 什麼是非阻塞
• Non-blocking
• Doesn't cause the caller (Thread) to
be blocked waiting for a result,
from Playframework: Async, Reactive, Threads, Futures, ExecutionContexts
https://gist.github.com/sadache/4714280
9. // 10 seconds
Image image1 = download(...);
render(image1);
// 12 seconds
Image image2 = download(...);
render(image2);
13. Thread 的缺點
• 常需配合用 synchronized, wait, notify
和 join
• 不同 Thread 間如何存取同一個變數
• 如何控管?
• 如何組合相依的工作
15. new Thread(() -> {
final Data result = fetchData(...);
Image image = download(data.avatar);
Bitmap bitmap = decode(image);
...
}).start();
34. CF<String> cf = CompletableFuture
.completableFuture("Value");
String result = cf.get();
35. CF<String> cf = CompletableFuture
.completableFuture("Value");
String result = cf.join();
36. CF<String> cf = CompletableFuture
.completableFuture("Value");
cf.thenAccept(
s -> System.out.println(s)
);
38. CF<String> cf = CompletableFuture
.supplyAsync(() -> load(),
executorService);
39. CF<String> cf = ...;
CF<Integer> length = cf.thenApply(
data -> data.length()
);
43. CF<String> cf = new
CompletableFuture();
cf.thenAccept(
s -> System.out.println(s)
);
44. CF<String> cf = new
CompletableFuture();
executor.submit(() -> {
String result = load();
cf.complete(result);
});
45. executor.submit(() -> {
try {
String result = load();
cf.complete(result);
} catch(Exception e) {
cf.completeExceptionally(e);
}
});
51. CF<File> cf = findUser(12L)
.thenCompose(
user -> download(user)
);
52. CF<File> cf = findUser(12L)
.thenCompose(
user -> download(user)
)
.thenCompose(
img -> save(img)
);
54. allOf
CF<String> api1 = ...;
CF<String> api2 = ...;
CF<String> api3 = ...;
CF<Void> all =
CompletableFuture.allOf(api1,
api2, api3);
56. anyOf
CF<String> api1 = ...;
CF<String> api2 = ...;
CF<String> api3 = ...;
CF<Object> all =
CompletableFuture.anyOf(api1,
api2, api3);
59. 同時多 key 查詢
CF<Value> executeQuery(String id);
List<CF<Value>> queries =
ids.stream()
.map(id -> executeQuery(id))
.collect(toList());
//using allOf to let
//List<CF<Value>> -> CF<List<Value>>
63. • 事件驅動 (event driven)
• 容易組合 (easy to compose)
• 控制權可以回給呼叫者
• 減少 thread 的浪費
優點
67. 支援非同步的 WEB 框架
• Servlet 3.0 AsyncContext
• Spring Framework
• Controller 的回傳直接用 CompletableFuture
• Play Framework
• Asynchronous web framework
• play.libs.F.Promise
68. Web application
• 該不該用處理 http 的 thread 做事?
• Tomcat 有 max-threads 設定
• Play 本來就是 http 跟 worker 分離
• 每個要求的工作時間不一定相同
• 花多少時間?佔多少比例?
• 花時間的工作有沒有資源存取上限?
69. Simple Test
• Job: 1500ms ~ 30%, 100ms ~ 70%
• 無處理上限
• Tomcat max-threads 200
• ab -n 1000 -c 400
• Async ~375 requests/second
• Sync ~300 requests/second
70. Simple Test
• Job: 1500ms ~ 50%, 100ms ~ 50%
• 一次只能處理 30 件 1500 ms 的工作
• Async ~36 requests/second
• 50% < 2000ms
• Sync ~39 requests/second
• 50% < 5900ms
71. Android 不支援
Java 8 API
• Guava
• ListenableFuture
• RxJava
• Reactive Programming
• Bolts-Android
• Lambda !?