Предположим, я хочу использовать кеш в DownloadQueue подобном примере.Радость сопрограмм заключается в том, что простая структура данных (например, HashMap
) может использоваться в однопоточном алгоритме.
Однако я хочу использовать ограниченный кэш и исключать дополнительные записи в более медленное постоянное хранилище.,Например, я могу взять Guava
+ CacheBuilder
+ RemovalListener
: https://github.com/google/guava/wiki/CachesExplained#removal-listeners
Вот проблема: RemovalListener
- это не приостановленный обратный вызов, поэтому нет способа отправить данные в Channels
или что-то еще из обратного вызова.
// This is placed in a suspend context (e.g. within `actor`)
val cache = CacheBuilder.newBuilder().maximumSize(1000)
.expireAfterWrite(10, TimeUnit.SECONDS)
.removalListener<Key, Value> { n ->
expireChannel.sendBlocking(n.value!!) // <-- could sendBlocking be used here???
}.build<Key, Value>()
Насколько я понимаю, runBlocking
блокирует выполнение текущего потока, таким образом, он блокирует текущую сопрограмму и не сможет получить /обрабатывать данные.
Есть ли способ сделать RemovalListener
-подобные обратные вызовы дружественными к сопрограммам?
Я могу представить себе обходной путь использования неограниченной очереди, заполненной RemovalListener
в то время как рассматриваемая сопрограмма в конечном итоге проверяет очередь.