android jetpack compose中的“remember”和“mutableState”有啥区别?

Posted

技术标签:

【中文标题】android jetpack compose中的“remember”和“mutableState”有啥区别?【英文标题】:What is the difference between "remember" and "mutableState" in android jetpack compose?android jetpack compose中的“remember”和“mutableState”有什么区别? 【发布时间】:2021-05-16 01:42:53 【问题描述】:

我是 jetpack compose 的新手,并试图了解 remembermutableStateOf 之间的区别

换句话说,这条线之间的尊重

val text = remember mutableStateOf("") 

还有这个

val text = remember "" 

还有这个

val text = mutableStateOf("")

【问题讨论】:

【参考方案1】:

remember 是一个可组合的函数,可用于缓存昂贵的操作。您可以将其视为可组合的本地缓存。

val state: Int = remember  1 

上述代码中的state 是不可变的。如果您想更改该状态并更新 UI,您可以使用MutableStateCompose 观察对MutableState 对象的任何读取和写入,并触发recomposition 以更新 UI。

val state: MutableState<Int> = remember  mutableStateOf(1) 

Text(
   modifier = Modifier.clickable  state.value += 1 ,
   text = "$state.value",
 )

另一个变体(在alpha12 中添加)称为rememberSaveable,类似于remember,但存储的值可以在进程死亡或配置更改后继续存在。

val state: MutableState<Int> = rememberSaveable  mutableStateOf(1) 

注意:您还可以使用属性委托作为语法糖来解开MutableState

var state: Int by remember  mutableStateOf(1) 

关于您问题的最后一部分,如果您在可组合物中执行如下所示的操作,那么您只是在创建一个 MutableState 对象。

val state: MutableState<Int> = mutableStateOf  1 

MutableState 是使用 LiveDataFlow 的替代方法。 Compose 默认情况下不会观察到此对象的任何更改,因此不会发生重组。如果您希望观察更改并缓存状态,请使用remember。如果不需要缓存只想观察,可以使用derivedStateOf。这是sample 的使用方法。

【讨论】:

您能检查一下问题的编辑吗? @ckunder @AhmedM.Abdalla 我已经更新了我的答案。【参考方案2】:

据我了解。

remember 只是缓存计算结果在组合之间保留结果实例。任何物体。和MutableState 实例。这就是它有用的原因。

val text = remember "" 

只缓存空字符串。

val text = mutableStateOf("")

创建MutableStatecompose 观察它的值,但不缓存MutableState 实例,所以它会在下一次重组时重新创建(当然如果重组会发生在这个地方)

例如:

val state: MutableState<Int> =  mutableStateOf(1)
println(state.toString())
Text(
    modifier = Modifier.clickable  state.value += 1 ,
    text = "$state.value",
)

文本将始终为 1,因为每次重组都会重新创建 state,并且输出将是:

MutableState(value=1)@227069120
MutableState(value=1)@104526071
MutableState(value=1)@915621104
MutableState(value=1)@580489706 

remember 缓存 MutableState 对象并在每次重组时保持相同的实例

val state: MutableState<Int> = remember  mutableStateOf(1) 
println(state.toString())
Text(
    modifier = Modifier.clickable  state.value += 1 ,
    text = "$state.value",
)

按预期工作。

MutableState(value=2)@1121832406
MutableState(value=3)@1121832406
MutableState(value=4)@1121832406
MutableState(value=5)@1121832406

记住(键)

val key = remember  0 
var state by remember(key)  mutableStateOf(1) 
println(state.toString())
Text(
    modifier = Modifier.clickable  state += 1 ,
    text = "$state",
)

即使key 没有改变,也像上面的例子一样工作。这是因为在 MutableState 的情况下,缓存的不是值,而是 MutableState 的实例本身带有 value 字段,它会发生变化。

更改 key 值将重新创建 MutableState 实例

【讨论】:

这个答案给出了根本原因:重复调用fun时保留状态数据,否则会重复初始化。【参考方案3】:

如果remember 与字段一起使用,则其值将在重新组合中保持不变。

如果mutableState 与字段一起使用,则只要字段值更改,所有使用该字段的可组合项都将重新组合。

【讨论】:

【参考方案4】:

基本上,在第一个示例中,您存储一个可变值,而在第二个示例中,您存储一个不可变值。

根据文档:“您可以在缓存昂贵的 UI 操作(例如计算文本格式)时存储不可变值。记住的值存储在组合中,其中包含调用记住的组合。” Source

有关 mutableStateOf 的更多信息,请参阅文档 link。当您希望在您的值发生变化时重新组合您的 UI 时,您可以使用它。

【讨论】:

【参考方案5】:

remember 关键字可以存储可变或不可变对象。如果你传递 mutableStateOf 来记住,只要该对象的值发生变化,它就会强制重新组合正在读取该值的可组合项。

【讨论】:

以上是关于android jetpack compose中的“remember”和“mutableState”有啥区别?的主要内容,如果未能解决你的问题,请参考以下文章

Android Jetpack Compose 中的文本渐变

Android日志:Jetpack Compose中的布局

android jetpack compose中的“remember”和“mutableState”有啥区别?

Android jetpack compose中的按钮长按监听器

Jetpack Compose 和 Compose Navigation 如何处理 Android 活动?

Koin在KMM与Android Jetpack Compose中的应用