如何在 Jetpack Compose 中支持智能重组

Sun*_*vel 6 android-jetpack-compose compose-recomposition

Jetpack compose 文档表示,如果所有输入稳定且未更改,它可以跳过重组。稳定类型的定义是这样的......

稳定类型必须遵守以下合同:

  1. 对于相同的两个实例,两个实例的 equals 结果将永远相同。
  2. 如果该类型的公共属性发生变化,Composition 将会收到通知。
  3. 所有公共财产类型也都很稳定。

我无法清楚地理解这一点。有人可以向我解释一下 compose 如何检查类型是否稳定吗?我可以理解如果 compose 确定类型是稳定的,那么它将使用 equals 方法检查是否相等。但是如何说一个类是否稳定,以便我们能够尽可能地理解和支持智能重组呢?

我试着玩了一下,发现了以下内容。

This data class Student is not stable, even if I pass the same instance again, its recomposing


data class Student(
     var id:Int=1,
     var name:String="Anonymous")
Run Code Online (Sandbox Code Playgroud)

然而,当我们再次传递相同的实例时,以下类被视为稳定的并且有利于智能重组

This class is stable when all the public parameters are changed to val

data class Student(
     val id:Int=1,
     val name:String="Anonymous")
Run Code Online (Sandbox Code Playgroud)

所以,我可以理解所有公共属性都应该是不可变的。但令我困惑的是,下面的类也被视为稳定的并且支持智能重组。为什么?

This MainActivityVM class is considered Stable when passing like

@Composable
fun StudentList(viewModel:MainActivityVM){
   ...
}

class MainActivityVM : ViewModel() {

   val studentNames = mutableStateListOf<Student>()
   var textInputDialogState by mutableStateOf(TextInputDialogState())

   var publicMutableProperty:String = "This is mutable"
}
Run Code Online (Sandbox Code Playgroud)

所以,我无法确切地弄清楚 compose 如何检查稳定类型。有人可以帮助我理解这一点,以便我可以有效地支持代码中的智能重组吗?

Rit*_*esh 4

我无法清楚地理解这一点。有人可以向我解释一下 compose 如何检查类型是否稳定吗?

这些默认情况下都是稳定的

  • 所有原始值类型:Boolean、Int、Long、Float、Char 等。
  • 弦乐
  • 所有函数类型(lambda)

Compose 编译器会查看该类,如果任何一个字段是稳定的,则该类不能推断为稳定的。

  • 可变(它与 var 属性关联)
  • 具有不稳定的类型(如列表、映射等。默认情况下所有数据结构都是不稳定的,因为它们不是不可变的而是只读的)

另外,您可以依赖编译器,并在有疑问时让编译器告诉您类的稳定性。

您可以使用

tasks.withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompile).configureEach {
    kotlinOptions {
        freeCompilerArgs += [
                "-P",
                "plugin:androidx.compose.compiler.plugins.kotlin:reportsDestination=${buildDir}/composeReports"
        ]
    }
}
Run Code Online (Sandbox Code Playgroud)

它将在 composeReports 中创建类,您可以检查 compose 是否可以推断稳定性。

stable class YourClass {
  stable val value: CornerSize
  <runtime stability> = Stable
}
Run Code Online (Sandbox Code Playgroud)

生成的报告将类似于上面的伪代码格式。

https://github.com/androidx/androidx/blob/androidx-main/compose/compiler/design/compiler-metrics.md#classes--classestxt