irpas技术客

Android Room增删改查详解、报错的改正记录_梨轻巧_android room update

网络 5803

一 Room介绍

Room 是 SQLite的封装SQLite: 需要写帮助类、SQL语句、执行SQL语句、创建表 → ?非常非常繁琐Room(SQLite的封装): 面向注解开发 @Entity @Dao @Database → 方便

通过在实体类上加注解@Entity,让实体类相当于一张表

通过在Dao接口上加注解@Dao,就可以让dao轻松地完成增删改查

创建一个类继承RoomDatabase,加注解@Database,轻松地建数据库和建表

二 案例代码

用Room完成如下增删改查功能

?1 导入依赖,同步 def room_version = "2.2.0-alpha01" implementation "androidx.room:room-runtime:$room_version"; annotationProcessor "androidx.room:room-compiler:$room_version"

2 创建一个实体类,加注解@Entity package room; import androidx.room.ColumnInfo; import androidx.room.Entity; import androidx.room.Ignore; import androidx.room.PrimaryKey; //一张表 //@Entity(tableName = "student_table"):tableName给表起别名,不写tableName表名就和java 类名一样 @Entity public class Student { @PrimaryKey(autoGenerate = true)//主键自增 @ColumnInfo(name = "_id")//定义数据库列名为 _id private int id; private String name; private int age; public Student() { } @Ignore public Student(String name, int age) { this.name = name; this.age = age; } @Ignore public Student(int id, String name, int age) { this.id = id; this.name = name; this.age = age; } public int getId() { return id; } public void setId(int id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public String toString() { return "Student{" + "id=" + id + ", name='" + name + '\'' + ", age=" + age + '}'; } } 3 创建一个Dao接口,加注解@Dao package room; import androidx.room.Dao; import androidx.room.Delete; import androidx.room.Insert; import androidx.room.Query; import androidx.room.Update; import java.util.List; @Dao public interface StudentDao { //新增(可变参数) @Insert void insertStudents(Student... students); //条件删除 @Delete void deleteStudents(Student... students); //修改(可变参数) @Update void updateStudents(Student... students); //条件查询多个 @Query("select * from student where name=:name") List<Student> getStudents(String... name); //条件查询1个 @Query("select * from student where _id=:id") Student getStudent(int... id); //查询所有 @Query("select * from student") List<Student> getAllStudents(); //删除所有 → '所有'的只能用@Query,@Query可以编写任意的sql语句 @Query("DELETE FROM student") void deleteAllStudents(); } 4 创建类继承RoomDatabase,加注解@Database package room; import android.content.Context; import androidx.room.Database; import androidx.room.Room; import androidx.room.RoomDatabase; //数据库关联之前的表和增删改查数据信息 @Database(entities = {Student.class},version = 2,exportSchema = false) public abstract class StudentDatabase extends RoomDatabase { //单例模式 返回db private static StudentDatabase INSTANCE; //用户只需要操作dao,必须暴露dao,dao被用户拿到后,就能进行增删改查了 public abstract StudentDao getStudentDao(); public static synchronized StudentDatabase getInstance(Context context){ if(INSTANCE == null){ INSTANCE = Room.databaseBuilder (context.getApplicationContext(),StudentDatabase.class,"say.db") //数据库默认是异步线程 //慎用:强制开启 主线程也可以操作数据库(测试可以用,真实环境不要用) .allowMainThreadQueries() .build(); } return INSTANCE; } } 5?获取数据库的实例获取dao调用方法 package com.example.mydatastroe; import androidx.appcompat.app.AppCompatActivity; import android.os.Bundle; import android.util.Log; import android.view.View; import java.util.ArrayList; import java.util.List; import room.Student; import room.StudentDatabase; public class MainActivity4 extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main4); } //新增:2个学生 public void insert(View view) { //id 自增不用赋值 Student student1 = new Student("小蓝", 12); Student student2 = new Student("小紫", 8); StudentDatabase.getInstance(this).getStudentDao(). insertStudents(student1,student2); } //条件删除:删除id为1的学生 public void delete(View view) { Student student = new Student(); student.setId(1); StudentDatabase.getInstance(this).getStudentDao().deleteStudents(student); } //修改id为3的学生为 白老板 100岁 public void update(View view) { Student student = new Student(3,"白老板",100); StudentDatabase.getInstance(this).getStudentDao().updateStudents(student); } //条件查询:查询姓名为"小蓝"的学生 public void queryMany(View view) { Log.e("cs", "-----------------条件查询多个----------------------"); List<Student> list = StudentDatabase.getInstance(this).getStudentDao().getStudents("小蓝"); for (Student student : list) { Log.e("cs", student.toString()); } } //条件查询:查询id为2的学生 public void queryOne(View view) { Log.e("cs", "-----------------条件查询1个----------------------"); Student student = StudentDatabase.getInstance(this).getStudentDao().getStudent(2); Log.e("cs", student.toString()); } //查询所有 public void queryAll(View view) { Log.e("cs", "-----------------查询所有----------------------"); List<Student> list = StudentDatabase.getInstance(this).getStudentDao().getAllStudents(); for (Student student : list) { Log.e("cs", student.toString()); } } //删除所有 public void deleteAll(View view) { StudentDatabase.getInstance(this).getStudentDao().deleteAllStudents(); Log.e("cs", "已删除所有数据"); } }

附上布局的文件

<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" tools:context=".MainActivity4"> <Button android:text="增" android:onClick="insert" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <Button android:text="删" android:onClick="delete" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <Button android:text="改" android:onClick="update" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <Button android:text="查多" android:onClick="queryMany" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <Button android:text="查1" android:onClick="queryOne" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <Button android:text="查所有" android:onClick="queryAll" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <Button android:text="删所有" android:onClick="deleteAll" android:layout_width="wrap_content" android:layout_height="wrap_content"/> </LinearLayout>

启动程序之后,Room框架会自动生成这2个文件

效果

?总结使用步骤

1 导入依赖,同步 ?? ?//Room的支持 ? ? def room_version = "2.2.0-alpha01" ? ? implementation "androidx.room:room-runtime:$room_version"; ? ? annotationProcessor "androidx.room:room-compiler:$room_version" ? ?? 2 创建一个实体类Student,加注解@Entity就相当于一张表 ?? ? 3 创建一个接口StudentDao,加注解@Dao就可以完成增删改查? ?? ?(Dao: database access object) ?? ? 4 创建抽象类StudentDatabase继承RoomDatabase,加注解@Database相当于是数据库 ?? ?单例模式返回db (创建数据库) ?? ?暴露dao ?? ? 5 获取数据库的实例获取dao调用方法 ?? ?StudentDatabase.getInstance(this).getStudentDao().getAllStudents() ?

三 报错及改正 3.1?@Ignore

错误:

错误: Room cannot pick a constructor since multiple constructors are suitable. Try to annotate unwanted constructors with @Ignore.

改正:

实体类不能有多个主构造方法,解决办法是只留一个常用的构造方法,剩下的构造方法加注解 @Ignore

?3.2?allowMainThreadQueries()

错误:

IllegalStateException: Cannot access database on the main thread since it may potentially lock the UI for a long period of time

改正:

调用这个方法让主线程也可以操作数据库

?3.3?查询方法参数错误

错误:

错误: Query method parameters should either be a type that can be converted into a database column or a List / Array that contains such type. You can consider adding a Type Adapter for this.

百度翻译一下:

查询方法参数应该是可以转换为数据库列的类型,或者是包含此类类型的列表/数组。可以考虑为此添加类型适配器。

错误代码如下

用@Query查询的时候,参数传的实体类,实体类不能转化成数据库里的列!

改正:


1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,会注明原创字样,如未注明都非原创,如有侵权请联系删除!;3.作者投稿可能会经我们编辑修改或补充;4.本站不提供任何储存功能只提供收集或者投稿人的网盘链接。

标签: #Android #room #update # #SQLite的封装SQLite