下面是对“第8天:数据存储”该文学习的更深层次的补充材料,对 MainActivity.kt
文件的理解。
下面对`MainActivity.kt’ 文件中每一行进行详细解释:
package com.example.datastoragedemo
这行指定了代码的包名,通常对应于项目的目录结构。
import android.content.SharedPreferences
import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import androidx.room.Room
import androidx.viewbinding.ViewBinding
import com.example.datastoragedemo.databinding.ActivityMainBinding // 导入生成的Binding类
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.runBlocking
这里导入了需要的类和库,包括SharedPreferences
(用于存储偏好设置)、Bundle
(用于活动状态)、AppCompatActivity
(支持兼容的活动)、Room
(用于数据库操作)以及ViewBinding
(简化视图访问)。还导入了协程库,用于处理异步任务。
class MainActivity : AppCompatActivity() {
定义了一个MainActivity
类,继承自AppCompatActivity
,这是Android活动的基础类。
private lateinit var binding: ActivityMainBinding // 声明View Binding变量
声明一个ActivityMainBinding
类型的变量binding
,使用lateinit
,表示稍后初始化。
private lateinit var sharedPreferences: SharedPreferencesprivate lateinit var userDao: UserDao
声明SharedPreferences
和UserDao
的变量,分别用于访问用户偏好设置和数据库操作。
override fun onCreate(savedInstanceState: Bundle?) {super.onCreate(savedInstanceState)
重写onCreate
方法,这是活动创建时调用的方法。调用super.onCreate
以确保父类正确初始化。
// 使用View Bindingbinding = ActivityMainBinding.inflate(layoutInflater)setContentView(binding.root)
通过ActivityMainBinding.inflate
方法初始化binding
,然后将布局设置为binding.root
,这使得可以通过binding
直接访问视图。
sharedPreferences = getSharedPreferences("user_prefs", MODE_PRIVATE)
初始化sharedPreferences
,以获取名为user_prefs
的共享偏好设置,使用私有模式存储。
userDao = UserDatabase.getDatabase(applicationContext).userDao()
通过UserDatabase
获取数据库实例,并获取userDao
以执行数据库操作。
binding.buttonSave.setOnClickListener { // 使用Binding访问视图saveToSharedPreferences()}
为buttonSave
设置点击事件监听器,点击时调用saveToSharedPreferences
方法。
binding.buttonRoom.setOnClickListener {saveToRoom()}
为buttonRoom
设置点击事件监听器,点击时调用saveToRoom
方法。
private fun saveToSharedPreferences() {val username = binding.editTextUsername.text.toString()val age = binding.editTextAge.text.toString().toIntOrNull() ?: 0
定义saveToSharedPreferences
方法,从EditText
中获取用户名和年龄。toIntOrNull()
将字符串转换为整数,如果转换失败则使用默认值0。
val editor = sharedPreferences.edit()editor.putString("username", username)editor.putInt("age", age)editor.apply()
获取SharedPreferences.Editor
实例,通过putString
和putInt
方法保存用户名和年龄,最后调用apply()
异步保存数据。
displayData()}
调用displayData
方法,显示已存储的数据。
private fun saveToRoom() {val username = binding.editTextUsername.text.toString()val age = binding.editTextAge.text.toString().toIntOrNull() ?: 0
定义saveToRoom
方法,同样从EditText
中获取用户名和年龄。
CoroutineScope(Dispatchers.IO).launch {userDao.insert(User(name = username, age = age))displayDataFromRoom()}
使用CoroutineScope
在IO线程中启动协程,插入用户数据到数据库,并调用displayDataFromRoom
方法。
private fun displayData() {// 获取所有存储的数据val allPrefs = sharedPreferences.allval userText = StringBuilder()
定义displayData
方法,获取所有存储的共享偏好设置,并初始化一个StringBuilder
用于格式化输出。
allPrefs.forEach { (key, value) ->userText.append("$key: $value\n") // 格式化输出}
遍历所有偏好设置,通过append
方法将每对键值对格式化为字符串并添加到userText
中。
binding.textViewOutput.text = "SharedPreferences:\n$userText"}
将格式化后的字符串显示在textViewOutput
中。
private fun displayDataFromRoom() {CoroutineScope(Dispatchers.IO).launch {val users = userDao.getAllUsers()val userText = users.joinToString { "${it.name}, Age: ${it.age}" }
定义displayDataFromRoom
方法,在IO线程中启动协程,获取所有用户数据,并使用joinToString
将用户名称和年龄格式化为字符串。
runOnUiThread {binding.textViewOutput.text = "Room Data:\n$userText"}}}
}
使用runOnUiThread
将结果更新到UI线程中,显示Room中的用户数据在textViewOutput
中。
这个代码实现了通过SharedPreferences
和Room
来存储和展示用户数据的功能。