Наблюдаемый на карте, чтобы определить, когда добавляется, обновляется удаленная запись - PullRequest
1 голос
/ 04 июня 2019

У меня есть карта, в моем случае ConcurrentHashMap<String, Device>, которая обновляется при получении некоторых событий через веб-сокет. Я хочу реализовать наблюдаемую на этой карте, чтобы знать, когда запись добавляется, обновляется или удаляется. Я пробовал с ObservableProperty, но никакие методы не вызываются при изменении карты.

var deviceCache : ConcurrentHashMap<String, Device> by MyObservable(ConcurrentHashMap())

 class MyObservable<T, V>(initialValue: ConcurrentHashMap<T, V>) : ObservableProperty<ConcurrentHashMap<T, V>>(initialValue) {
override fun afterChange(property: KProperty<*>, oldValue: ConcurrentHashMap<T, V>, newValue: ConcurrentHashMap<T, V>) {
  super.afterChange(property, oldValue, newValue)
  log.e("new value is $newValue")
}

override fun beforeChange(property: KProperty<*>, oldValue: ConcurrentHashMap<T, V>, newValue: ConcurrentHashMap<T, V>): Boolean {
  log.e("beforeChange called")
  return super.beforeChange(property, oldValue, newValue)
}

}

Может кто-нибудь помочь мне, как я могу решить это?

1 Ответ

3 голосов
/ 04 июня 2019

Проблема в том, что Map не является свойством, вы не можете использовать делегаты свойств таким способом.Вам нужно написать декоратор для Map следующим образом:

class ObservableMap<K, V>(private val map: MutableMap<K, V>) : MutableMap<K, V> by map {

    override fun put(key: K, value: V): V? {
        TODO("not implemented")
    }

    override fun putAll(from: Map<out K, V>) {
        TODO("not implemented")
    }

    override fun remove(key: K): V? {
        TODO("not implemented")
    }

}

Здесь мы делегируем все операции поддержке map, и вам нужно только реализовать свою логику при добавлении / удалениив описанных выше методах.

Я не уверен, что вы подразумеваете под update, но если вы имеете в виду «значение на карте перезаписывается», то вы можете справиться с этим в put.

Вы можете использовать это ObservableMap следующим образом:

val map = ObservableMap(ConcurrentHashMap<String, String>())

Обратите внимание, что если вы хотите поддерживать операции ConcurrentHashMap, вам также необходимо включить overrides для AbstractMap<K,V> и ConcurrentMap<K,V>так как они добавляют некоторые новые операции, которые вы можете отслеживать.Приведенный выше код является лишь примером.

...