MutableLiveData rozszerza się z LiveData. Metody chronione LiveData mogą być adresowane tylko przez własne lub podklasy. W tym przypadku MutableLiveData będąca podklasą LiveData może uzyskać dostęp do tych chronionych metod.
To, co chciałbyś zrobić, to obserwować na instancji i zobaczyć, czy są jakieś zmiany. Ale jednocześnie nie chcesz, aby ktokolwiek z zewnątrz zmienił obserwowaną instancję. W pewnym sensie stwarza to problem, ponieważ chciałbyś mieć obiekt, który jest i można go zmieniać, aby aktualizować każdy nowy status i nie można go zmieniać, aby upewnić się, że nikt, kto nie powinien, nie może zaktualizować tej instancji. Te dwie funkcje są ze sobą sprzeczne, ale można je rozwiązać, tworząc dodatkową warstwę.
Więc to, co robisz, to rozszerzanie swojej klasy, LiveData, o klasę, która ma dostęp do jej metod. Warstwa podrzędna, w tym przypadku MutableLiveData, ma dostęp do chronionych metod swojego rodzica (/ super).
Teraz zaczynasz tworzyć instancje i tworzymy instancję obserwatora MutableLiveData. Jednocześnie tworzysz instancję LiveData odwołującą się do tej samej instancji. Ponieważ MutableLiveData rozszerza LiveData, każda instancja MutableLiveData jest obiektem LiveData i dlatego zmienna LiveData może się do niej odwoływać.
Teraz sztuczka jest prawie zakończona. Ujawniasz tylko instancję LiveData, nikt nie może używać jej chronionych metod, ani nie może przesyłać jej do super (być może w czasie kompilacji, ale nie działałaby: błąd RunTime). Zachowujesz prywatność rzeczywistej instancji podklasy, więc mogą ją zmienić tylko właściciele instancji, używając metod instancji.
//create instance of the sub class and keep this private
private val _name: MutableLiveData<String> = MutableLiveData<String>()
//create an instance of the super class referring to the same instance
val name: LiveData<String> = _name
//assign observer to the super class, being unable to change it
name.value.observe(.....)
Teraz superklasa powiadamia o zastosowaniu jakichkolwiek zmian.
_name.postValue(...)
Cytat blokowy Ogólnie rzecz biorąc, czy taka forma dziedziczenia (zwiększenie widoczności niektórych metod jest jedyną zmianą) jest dobrze znaną praktyką i jakie scenariusze mogą się przydać (zakładając, że mamy dostęp do całego kodu)?
Tak, jest to dość dobrze znane i ten opisany powyżej jest częstym scenariuszem. Usuń wzorzec obserwatora i po prostu utwórz go w formie set / get, przyniosłoby to równie duże korzyści. W zależności od tego, gdzie go wdrożysz, ostatecznie nie będzie żadnych złotych zasad.
LiveData
jest niezmienny, ponieważ klient nie może zmienić stanu wewnętrznego, dlatego jest bezpieczny