Reputation: 1223
I have a ViewModel
class that looks like this:
class EditUserViewModel(
private val initUser: User,
) : ViewModel() {
private val _user = MutableLiveData(initUser)
val user: LiveData<User>
get() = _user
fun hasUserChanged() = initUser != _user.value
}
User
can update some properties of the User data class instance through the UI.
To check if there are any changes when navigating from the fragment I use hasUserChanged
method.
The problem is that is always false. I checked and it seems that the initialUser
changes every time I change the _user MutableLiveData
.
Why is that? Is the initial value of MutableLiveData
passed by reference? I always thought that Kotlin is a "pass-by-value" type of language.
Update:
The problem seems to disappear when copying initUser
before putting it inside the MutableLiveData
.
private val _user = MutableLiveData(initUser.copy())
But it still doesn't make sense to me why I have to do that.
Upvotes: 1
Views: 1175
Reputation: 22832
Kotlin is like java and they are pass-by-value. If you implement the equals
function in User
class, or make it as data class
(which implements the equals
function implicitly), it makes you sure that the content of the user objects is checked by !=
operator.
Update
If you are changing the value of LiveData
directly, for example like this:
_user.value.name = "some name"
it means that you are changing the name
property of the initUser
, because _user.value
exactly refers to the object that the initUser
does. Consequently, the !=
operator always returns false, because we have one object with two references to it.
Now, when you are doing so:
private val _user = MutableLiveData(initUser.copy())
you are creating a deep copy of initUser
(let's call it X
) which is a new object in memory with the same property values of initUser
.
Thus, by changing its properties like: _user.value.name = "some name"
, in fact, you are making this change on X
, not initUser
. It leads to preserving the initial values in initUser
, meaning do not changing them, and solving the issue.
Upvotes: 1