Jetpack Compose创建ViewModel时出现ClassCastException异常求助
解决Jetpack Compose中
viewModel()触发ClassCastException异常问题 异常信息
FATAL EXCEPTION: main Process: com.github.profit, PID: 23095 java.lang.ClassCastException: java.lang.Object cannot be cast to androidx.lifecycle.ViewModel at androidx.lifecycle.ViewModelProvider$NewInstanceFactory.create(ViewModelProvider.kt:201) at androidx.lifecycle.ViewModelProvider$AndroidViewModelFactory.create(ViewModelProvider.kt:322) at androidx.lifecycle.ViewModelProvider$AndroidViewModelFactory.create(ViewModelProvider.kt:304) at androidx.lifecycle.SavedStateViewModelFactory.create(SavedStateViewModelFactory.kt:175) at androidx.lifecycle.SavedStateViewModelFactory.create(SavedStateViewModelFactory.kt:138) at androidx.lifecycle.ViewModelProvider.get(ViewModelProvider.kt:187) at androidx.lifecycle.ViewModelProvider.get(ViewModelProvider.kt:153) at androidx.lifecycle.viewmodel.compose.ViewModelKt.get(ViewModel.kt:215) at androidx.lifecycle.viewmodel.compose.ViewModelKt.viewModel(ViewModel.kt:156) at com.github.profit.MainActivityKt.ProductInfo(MainActivity.kt:136) ...
相关代码与配置
MainActivity
class MainActivity : ComponentActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContent { ProfitTheme { Surface( modifier = Modifier.fillMaxSize(), color = MaterialTheme.colors.background ) { ProductInfo() } } } } }
ProductInfo
@Composable fun ProductInfo() { val viewModel: ProductsViewModel by viewModel() Column { TextField( value = viewModel.product1Price, onValueChange = { viewModel.product1Price = it }, keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Number), label = { Text(text = "Price") }, placeholder = { Text(text = "Price in Ft") }, ) // ... } }
ProductsViewModel
class ProductsViewModel: ViewModel() { private val _product1Price = mutableStateOf(0U) private val _product1Quantity = mutableStateOf(0U) private val _product2Price = mutableStateOf(0U) private val _product2Quantity = mutableStateOf(0U) var product1Price: String get() = _product1Price.value.toString() set(value) = setField(_product1Price, value) // ... }
项目build.gradle
buildscript { ext { compose_ui_version = '1.1.1' lifecycle_version = '2.5.1' } } plugins { id 'com.android.application' version '7.3.1' apply false id 'com.android.library' version '7.3.1' apply false id 'org.jetbrains.kotlin.android' version '1.6.10' apply false }
应用模块build.gradle
plugins { id 'com.android.application' id 'org.jetbrains.kotlin.android' } android { namespace 'com.github.profit' compileSdk 32 defaultConfig { applicationId "com.github.profit" minSdk 22 targetSdk 32 versionCode 1 versionName "1.0" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" vectorDrawables { useSupportLibrary true } } buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' } } compileOptions { sourceCompatibility JavaVersion.VERSION_1_8 targetCompatibility JavaVersion.VERSION_1_8 } kotlinOptions { jvmTarget = '1.8' } buildFeatures { compose true } composeOptions { kotlinCompilerExtensionVersion '1.1.1' } packagingOptions { resources { excludes += '/META-INF/{AL2.0,LGPL2.1}' } } } dependencies { implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycle_version" implementation "androidx.lifecycle:lifecycle-viewmodel-compose:$lifecycle_version" implementation "androidx.lifecycle:lifecycle-runtime-ktx:$lifecycle_version" implementation 'androidx.core:core-ktx:1.7.0' implementation 'androidx.activity:activity-compose:1.3.1' implementation "androidx.compose.ui:ui:$compose_ui_version" implementation "androidx.compose.ui:ui-tooling-preview:$compose_ui_version" implementation 'androidx.compose.material:material:1.1.1' testImplementation 'junit:junit:4.13.2' androidTestImplementation 'androidx.test.ext:junit:1.1.4' androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.0' androidTestImplementation "androidx.compose.ui:ui-test-junit4:$compose_ui_version" debugImplementation "androidx.compose.ui:ui-tooling:$compose_ui_version" debugImplementation "androidx.compose.ui:ui-test-manifest:$compose_ui_version" }
问题原因分析
该异常是因为ViewModelProvider无法正确创建ProductsViewModel实例,核心原因可能是泛型推断异常、依赖版本不兼容或项目缓存问题。
解决方案
1. 显式指定ViewModel泛型参数
修改ProductInfo中的viewModel获取代码,显式声明泛型类型,避免Kotlin泛型擦除导致的推断错误:
@Composable fun ProductInfo() { val viewModel: ProductsViewModel by viewModel<ProductsViewModel>() Column { // ... 原有代码 } }
2. 升级依赖版本确保兼容性
当前使用的Compose 1.1.1与Lifecycle 2.5.1虽理论兼容,但升级到更稳定的匹配版本可避免潜在冲突:
- 修改项目根目录
build.gradle:
buildscript { ext { compose_ui_version = '1.2.1' lifecycle_version = '2.6.1' kotlin_version = '1.7.10' } } plugins { id 'com.android.application' version '7.4.2' apply false id 'com.android.library' version '7.4.2' apply false id 'org.jetbrains.kotlin.android' version "${kotlin_version}" apply false }
- 修改模块
build.gradle中的composeOptions:
composeOptions { kotlinCompilerExtensionVersion '1.2.1' }
- 同步项目依赖。
3. 验证ViewModel类的正确性
确认ProductsViewModel正确导入androidx.lifecycle.ViewModel,且构造函数为public(Kotlin默认即为public):
import androidx.lifecycle.ViewModel class ProductsViewModel: ViewModel() { // ... 原有代码 }
4. 清理缓存并重建项目
- 执行
File -> Invalidate Caches... -> Invalidate and Restart - 执行
Build -> Clean Project - 执行
Build -> Rebuild Project
内容的提问来源于stack exchange,提问作者gojoGS
相关产品推荐
相关产品推荐

