Android-Jetpack-Room数据库

2022-04-22  本文已影响0人  阿博聊编程
配图来自网络,如侵必删

在日常开放当中,我们肯定会遇到要将数据存储在本地的需求。在Jetpack全家桶中有提供Room数据库给我们使用,帮助我们存储数据。这篇博客就说说Room数据库的知识,希望对看文章的小伙伴有所启发。

Room

Room是在SQLite的基础上提供了一个抽象层,让我们充分利用SQLite的性能同时,还能写出更健壮的数据库相关的代码。

Room相关的依赖

Room基础依赖:

 implementation "androidx.room:room-runtime:2.4.2"
annotationProcessor "androidx.room:room-compiler:2.4.2"

配合RxJava2使用,新增依赖如下:

 implementation "androidx.room:room-rxjava2:2.4.2"

配合RxJava3使用,新增依赖如下:

implementation "androidx.room:room-rxjava3:2.4.2"

配合Paging 3使用,新增依赖如下:

implementation "androidx.room:room-paging:2.5.0-alpha01"

Room架构图

配图来自网络,如侵必删

架构中的相关类和对象:

概括就是:

一个Entity代表一张表,而每张表都需要一个Dao对象,用于对表进行增/删/改/查。Room数据库在被实例化之后,我们就可以通过数据库实例得到Dao对象(GetDao),进而通过Dao对象对表中的数据进行操作。

Room字段注解

Room简单使用

1.创建一个Entity类,代码如下:

import androidx.room.PrimaryKey
import androidx.room.ColumnInfo
import androidx.room.Entity
import androidx.room.Ignore

@Entity(tableName = "student")
class Student {
    @PrimaryKey(autoGenerate = true)
    @ColumnInfo(name = "id", typeAffinity = ColumnInfo.INTEGER)
    var id: Int = 0

    @ColumnInfo(name = "name", typeAffinity = ColumnInfo.TEXT)
    var name: String

    @ColumnInfo(name = "age", typeAffinity = ColumnInfo.TEXT)
    var age: String

    /**
     * Room默认使用这个构造器操作数据
     */
    constructor(id: Int, name: String, age: String) {
        this.id = id
        this.name = name
        this.age = age
    }

    /**
     * 告诉Room忽略这个构造器
     */
    @Ignore
    constructor(name: String,age: String) {
        this.name = name
        this.age = age
    }
}

2.针对Entity类,创建一个Dao类,代码如下:

import androidx.room.*

@Dao
interface StudentDao {
    @Insert
    fun insertStudent(student: Student?)

    @Delete
    fun deleteStudent(student: Student?)

    @Update
    fun updateStudent(student: Student?)

    /**
     * 查询学生列表
     */
    @Query("SELECT * FROM student")
    fun studentList(): List<Student>

    /**
     * 通过id查询某个学生
     */
    @Query("SELECT * FROM student WHERE id = :id")
    fun getStudentById(id: Int): Student?
}

3.创建数据库代码如下:

import android.content.Context
import androidx.room.Database
import androidx.room.RoomDatabase
import androidx.room.Room

@Database(entities = [Student::class], version = 1)
abstract class MyDatabase : RoomDatabase() {

    abstract fun studentDao(): StudentDao

    companion object {

        private const val DATABASE_NAME = "my_db.db"
        @Volatile
        private var INSTANCE: MyDatabase? = null

        fun getInstance(context: Context): MyDatabase = INSTANCE?: synchronized(this){
            INSTANCE ?: buildDatabase(context).also { INSTANCE = it }
        }

        private fun buildDatabase(context: Context) =
            Room.databaseBuilder(context.applicationContext, MyDatabase::class.java, DATABASE_NAME)
                .allowMainThreadQueries().build()


    }
}

4.增删改查方法:
初始化数据库:

val myDatabase = MyDatabase.getInstance(this)

插入数据:

myDatabase?.studentDao()?.insertStudent(Student("阿博","23"))

更新数据:

myDatabase?.studentDao()?.updateStudent(Student("阿博","24"))

删除数据:

myDatabase?.studentDao()?.deleteStudent(Student("阿博","24"))

查询所有的学生:

myDatabase?.studentDao()?.studentList()

查询单个学生:

myDatabase?.studentDao()?.getStudentById(0)

遇到cannot find implementation for xxxxxx does not exist

遇到这个错误的原因是我们使用Kotlin开发项目,依赖需要修改成:

 kapt "androidx.room:room-compiler:2.4.2"

如果使用这个报错,那就是因为我们项目里面没有使用:

apply plugin: 'kotlin-kapt'

遇到编译错误

Schema export directory is not provided to the annotation processor so we cannot export the schema. You can either provide room.schemaLocation annotation processor argument OR set exportSchema to false.

Android官方推荐做法:

android {
    ...
    defaultConfig {
        ...
        javaCompileOptions {
            annotationProcessorOptions {
                arguments += [
                    "room.schemaLocation":"$projectDir/schemas".toString(),
                    "room.incremental":"true",
                    "room.expandProjection":"true"]
            }
        }
    }
}
上一篇 下一篇

猜你喜欢

热点阅读