Android Jetpack中Room的使用
作者:IT_zhazhanan 发布时间:2021-11-11 08:43:36
Room
Room主要分三个部分 database、dao和实体类entity
Entity
entity实体类定义时需要用到@Entity(tableName = "student")注解,其中参数为表名
主键定义需要用到@PrimaryKey(autoGenerate = true)注解,参数决定是否自增长
每个属性(也就是表的字段)都需要加@ColumnInfo(name = "name",typeAffinity = ColumnInfo.TEXT)注解 ,name是表中的字段名、 typeAffinity是字段类型,类型有:
// 未定义类型关联。将基于类型进行解析。
int UNDEFINED = 1;
// 文本类型
int TEXT = 2;
// 整数或布尔值的列关联常数。
int INTEGER = 3;
// 用于浮点数或双精度数的列关联常数。
int REAL = 4;
// 二进制数据的列亲和常数。
int BLOB = 5;
实体类需要指定一个构造方法。如果我们有多个构造方法,那么就需要告诉room忽略其他的构造器,不然会报错,room只可以使用一个构造器。构造函数上加入@Ignore注解即可(想忽略一个属性也是)
@Entity(tableName = "student")
public class Student {
@PrimaryKey(autoGenerate = true)
@ColumnInfo(name = "id",typeAffinity = ColumnInfo.INTEGER)
public int id;
@ColumnInfo(name = "name",typeAffinity = ColumnInfo.TEXT)
public String name;
@ColumnInfo(name = "age",typeAffinity = ColumnInfo.INTEGER)
public int age;
@ColumnInfo(name = "sex",typeAffinity = ColumnInfo.INTEGER)
public int sex;
@Ignore// 告诉room忽略这个构造方法
public Student(int id, String name, int age) {
this.id = id;
this.name = name;
this.age = age;
}
@Ignore// 告诉room忽略这个构造方法
public Student(int id) {
this.id = id;
}
// 指定room用的构造方法
public Student(String name, int age) {
this.name = name;
this.age = age;
}
}
Dao
dao是一个interface,需要加入一个@Dao注解,内部主要声明一些对数据做操作的抽象方法,方法都需要加上room * 定的注解
@Insert 添加
@Update 修改
@Delete 删除
@Query 查询 此注解需要加入参数 参数就是sql语句
@Dao
public interface StudentDao {
@Insert
void insertStudent(Student...students);
@Query("SELECT * FROM student")
List<Student> getAllStudent();
@Query("SELECT * FROM student WHERE id=:id")
List<Student> getAllStudentById(int id);
@Query("DELETE FROM student")
void clearAll();
@Update
void upData(Student...students);
@Delete
void delete(Student...students);
}
DataBase
database类需要继承RoomDatabase这个抽象类,dataBase也必须是抽象类。需要加入@DataBase注解
@Database(entities =
{Student.class}, version = 1, exportSchema = false) // entities-实体类 version-数据库版本 exportSchema-是否生成schema文件,schema文件中包含的是表结构和信息
如果想生成schema文件 还需要在build.gradle中指定schema文件的生成位置
android {
compileSdkVersion 30
buildToolsVersion "30.0.3"
defaultConfig {
applicationId "com.example.room"
minSdkVersion 20
targetSdkVersion 30
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
//指定room.schemaLocation生成的文件路径
javaCompileOptions {
annotationProcessorOptions {
arguments = ["room.schemaLocation": "$projectDir/schemas".toString()]
}
}
}
}
database类需要是单例的 但是不需要写私有构造器,继承了RoomDatabase之后room会识别,只需要一个getInstance方法,内部是database的实例化。
public static synchronized StudentDataBase getInstance(Context context) {
if (mInstance == null) {
mInstance = Room.databaseBuilder(context.getApplicationContext(),
StudentDataBase.class,
DATABASE_NAME)
// .allowMainThreadQueries()// 允许在主线程操作数据库
.addMigrations(MIGRATION_1_2)// 数据库升级时
.fallbackToDestructiveMigration()// 数据库版本异常时 会清空原来的数据 然后转到目前版本
// .createFromAsset("资源文件中的初始数据库")// 预填充数据库 初始数据
.build();
}
return mInstance;
}
还需要声明一个获取dao的抽象方法,只声明即可。
public abstract StudentDao getStudentDao();
当数据库的版本有升级时,就需要使用到Migration,创建Migration(),参数为哪个版本到哪个版本的升级。重写mingrate方法,在mingrate方法内通过database.execSQL()方法来写表的变化(结构变化等)。Migration可以有多个,对应表的多次升级。
static final Migration MIGRATION_1_2 = new Migration(1, 2) {
@Override
public void migrate(@NonNull SupportSQLiteDatabase database) {
database.execSQL("ALTER TABLE student ADD COLUMN sex INTEGER NOT NULL DEFAULT 1");// 添加表字段
}
};
database全貌
@Database(entities = {Student.class}, version = 1, exportSchema = true)
public abstract class StudentDataBase extends RoomDatabase {
private static StudentDataBase mInstance;
private static final String DATABASE_NAME = "student.db";
public static synchronized StudentDataBase getInstance(Context context) {
if (mInstance == null) {
mInstance = Room.databaseBuilder(context.getApplicationContext(),
StudentDataBase.class,
DATABASE_NAME)
// .allowMainThreadQueries()// 允许在主线程操作数据库
.addMigrations(MIGRATION_1_2)// 数据库升级时
.fallbackToDestructiveMigration()// 数据库版本异常时 会清空原来的数据 然后转到目前版本
// .createFromAsset("资源文件中的初始数据库")// 预填充数据库 初始数据
.build();
}
return mInstance;
}
static final Migration MIGRATION_1_2 = new Migration(1, 2) {
@Override
public void migrate(@NonNull SupportSQLiteDatabase database) {
database.execSQL("ALTER TABLE student ADD COLUMN sex INTEGER NOT NULL DEFAULT 1");// 添加表字段
}
};
public abstract StudentDao getStudentDao();
}
使用
获取dao
StudentDataBase dataBase = StudentDataBase.getInstance(this);
StudentDao studentDao = dataBase.getStudentDao();
通过dao操作表,注意对数据库的操作需要放到子线程中操作
class GetAllStudentTask extends AsyncTask<Void,Void,List<Student>>{
@Override
protected List<Student> doInBackground(Void... voids) {
List<Student> allStudent = studentDao.getAllStudent();
for (int j = 0; j < allStudent.size(); j++) {
Log.i("student", "doInBackground: "+allStudent.get(j).name+"--id:"+allStudent.get(j).id);
}
return allStudent;
}
来源:https://blog.csdn.net/IT_zhazhanan/article/details/120724281
猜你喜欢
- Spring bean配置单例或多例模式单例spring bean 默认是单例默认,在对应.xml文件中的配置是:<bean id=&
- 1.将本地jar包放入本地仓库。只需执行如下命令即可:mvn install:install-file -Dfile=D:/demo/fib
- 问题描述在使用poi-tl word模版工具时,发现生成的文档中,图片格式为嵌入型,有的图片甚至被表格遮挡一半。而自己想要的图片格式为上下型
- Android的Camera相关应用开发中,有一个必须搞清楚的知识点,就是Camera的预览方向和拍照方向图像的Sensor方向:手机Cam
- 简单工厂模式:由一个工厂对象决定创建出哪一种类的实例。1.抽象类public abstract class People { p
- 相信大家都经常使用String 的split方法,但是大家有没有遇到下面的这种情况:大家想想下面的代码执行结果是什么public stati
- C#调用c++dll文件是一件很麻烦的事情,首先面临的是数据类型转换的问题,相信经常做c#开发的都和我一样把学校的那点c++底子都忘光了吧(
- 前言老规矩,还是从最简单粗暴的开始。那么多简单算简单?多粗暴算粗暴?我告诉你可以不写一句代码,你信吗?直接把一个文件往IIS服务器上一扔,就
- 导语在使用flutter 自带图片组件的过程中,大家有没有考虑过flutter是如何加载一张网络图片的? 以及对自带的图片组件我们可以做些什
- 一、DurationDuration主要用来衡量秒级和纳秒级的时间,使用于时间精度要求比较高的情况。先来看看Duration的定义:publ
- 1、每帧检查定义一个时间变量 timer,每帧将此时间减去帧间隔时间 Time.deltaTime,如果小于或者等于零,说明定时器到了,执行
- 项目里头需要做一个判断用户输入的号码是否是正确的手机号码,正确的手机号码应该是11位的,这里我们需要用一个正则表达式来进行判断,
- 最新开发新项目的时候,要做分享项目,要求分享有微信,微信朋友圈,QQ,QQ空间,新浪微博这五个,所分享内容包括,分享纯图片,纯文字,图文类型
- 前言:由于项目需求,短信验证码的接口需要换成阿里大于的,但是尴尬的发现阿里大于的jar包没有maven版本的,于是便开始了一上午的 * 引包之
- 本文实例讲述了C#动态加载dll扩展系统功能的方法。分享给大家供大家参考。具体分析如下:动态加载dll,主要是为了扩展功能,增强灵活性而实现
- 前言AOP(Aspect Oriented Programming),即面向切面编程,是Spring框架的大杀器之一。首先,我声明下,我不是
- 网络编程是指编写运行在多个设备(计算机)的程序,这些设备都通过网络连接起来。java.net包中J2SE的API包含有类和接口,它们提供低层
- 在LINUX上部署带有JAR包的JAVA项目首先eclipse上要装上一个小插件,叫做Fat Jar点击Fat Jar红框里选上主类点击Ne
- 前言我通常是不太关心代码的具体实现的,因为我的开发语言很杂,倾向于一些最简单通用的方式去解决。今儿不小心在群里看到一位朋友发了下面的java
- 一.相关知识:Java多线程程序设计到的知识:(一)对同一个数量进行操作(二)对同一个对象进行操作(三)回调方法使用(四)线程同步,死锁问题