1

ゴール:

最後にエンキューokhttp3.Callされたものが最初に実行される


試した解決策:LIFO Executor(機能しない)

Executor私はLIFO (LIFO順序付けのExecutor Service )の解決策を見つけ、この方法でこの種のものを適用ExecutorしましたOkHttpClient

private val httpClient = OkHttpClient.Builder().dispatcher(
        Dispatcher(ThreadPoolExecutor(..., LifoLinkedBlockingDequeue<Runnable>()))
    ).build()

しかし、これはうまくいきませんでした

分析

でソース コードをトレースしたokhttp3.Dispatcherところ、次のことがわかりました。

  1. まず、キューCallに入れられ(private final Deque<AsyncCall> readyAsyncCalls = new ArrayDeque<>())たすべてのものがDispatcher.java"
  2. 次に、これらCallの s はFIFOreadyAsyncCallsのブロッキング両端キューに移動されますExecutor
  3. 最後に、Calls inはLIFOExecutorに実行されます

私の場合、大量Callの s が同時に生成され、それらを消費するスレッドは比較的少なくなります。
--> ほとんどの s は、一時的 にではなくCallキューに入れられます--> LIFOは効果を再生しませんDispatcherExecutor
Executor

| Dispatcher: 1,2,3,4,5 | Executor:    | executing:    | done:          |
| Dispatcher: 2,3,4,5   | Executor:1   | executing:    | done:          |
| Dispatcher: 4,5       | Executor:2,3 | executing:1   | done:          |
| Dispatcher: 5         | Executor:4   | executing:3,2 | done:1         |
| Dispatcher:           | Executor:5   | executing:4   | done:1,3,2     |
| Dispatcher:           | Executor:    | executing:5   | done:1,3,2,4   |
| Dispatcher:           | Executor:    | executing:    | done:1,3,2,4,5 |
  • Calls は FIFO 順で からDispatcherに移動されExecutorますが、この手順は非常に「非効率的」です。
  • Call■ からExecutor実行状態までは LIFO 順です。Callしかし にはsが少なくExecutor、LIFO 効果は明ら​​かではありません。

これを達成する他の方法を知っている人はいますか?

4

2 に答える 2