国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 系統 > Android > 正文

Android架構組件Room的使用詳解

2019-10-22 18:18:24
字體:
來源:轉載
供稿:網友

Room其實就是一個orm,抽象了SQLite的使用,但是它作為Android的親兒子orm,并且原生支持LiveData和Rxjava嵌套使用,學習一下還是不錯的。

Room有3個主要組件

  • Database :數據庫
  • Entity : 代表數據庫一個表結構
  • Dao : 包含訪問數據庫的方法

簡單使用

添加Google Maven倉庫

allprojects {  repositories {    jcenter()    google()  }}

添加依賴

dependencies {  // Room  implementation "android.arch.persistence.room:runtime:1.0.0"  annotationProcessor "android.arch.persistence.room:compiler:1.0.0"}

定義數據表實體類

班級表

@Entity(tableName = "tb_class")public class ClassEntity {  @PrimaryKey  private long id;}

學生表

//指示數據表實體類@Entity(tableName = "tb_student",//定義表名    indices = @Index(value = {"name", "sex"}, unique = true),//定義索引    foreignKeys = {@ForeignKey(entity = ClassEntity.class,        parentColumns = "id",        childColumns = "class_id")})//定義外鍵public class StudentEntity {  @PrimaryKey //定義主鍵  private long id;  @ColumnInfo(name = "name")//定義數據表中的字段名  private String name;  @ColumnInfo(name = "sex")  private int sex;  @Ignore//指示Room需要忽略的字段或方法  private String ignoreText;  @ColumnInfo(name = "class_id")  private String class_id;  //setter and getter}

Entity注解可選參數

public @interface Entity { //定義表名  String tableName() default ""; //定義索引  Index[] indices() default {}; //設為true則父類的索引會自動被當前類繼承  boolean inheritSuperIndices() default false; //定義主鍵  String[] primaryKeys() default {}; //定義外鍵  ForeignKey[] foreignKeys() default {};}

Index索引注解可選參數

public @interface Index { //定義需要添加索引的字段 String[] value(); //定義索引的名稱 String name() default ""; //true-設置唯一鍵,標識value數組中的索引字段必須是唯一的,不可重復 boolean unique() default false;}

ForeignKey外鍵注解可選參數

public @interface ForeignKey { //引用外鍵的表的實體 Class entity(); //要引用的外鍵列 String[] parentColumns(); //要關聯的列 String[] childColumns(); //當父類實體(關聯的外鍵表)從數據庫中刪除時執行的操作 @Action int onDelete() default NO_ACTION; //當父類實體(關聯的外鍵表)更新時執行的操作 @Action int onUpdate() default NO_ACTION; //在事務完成之前,是否應該推遲外鍵約束 boolean deferred() default false; //給onDelete,onUpdate定義的操作 int NO_ACTION = 1; int RESTRICT = 2; int SET_NULL = 3; int SET_DEFAULT = 4; int CASCADE = 5; @IntDef({NO_ACTION, RESTRICT, SET_NULL, SET_DEFAULT, CASCADE}) @interface Action {  }}

定義Dao類

@Daopublic interface StudentDao {  @Query("SELECT * FROM StudentEntity")  List<StudentEntity> getAll();  @Query("SELECT * FROM StudentEntity WHERE id IN (:ids)")  List<StudentEntity> getAllByIds(long[] ids);  @Insert  void insert(StudentEntity... entities);  @Delete  void delete(StudentEntity entity);  @Update  void update(StudentEntity entity);}

@insert, @Update都可以執行事務操作,定義在OnConflictStrategy注解類中

public @interface Insert {  //定義處理沖突的操作  @OnConflictStrategy   int onConflict() default OnConflictStrategy.ABORT;}public @interface OnConflictStrategy {  //策略沖突就替換舊數據  int REPLACE = 1;  //策略沖突就回滾事務  int ROLLBACK = 2;  //策略沖突就退出事務  int ABORT = 3;  //策略沖突就使事務失敗   int FAIL = 4;  //忽略沖突  int IGNORE = 5;}

定義數據庫

@Database(entities = {StudentEntity.class}, version = 1)public abstract class RoomDemoDatabase extends RoomDatabase {  public abstract StudentDao studentDao();}

生成數據庫實例

RoomDemoDatabase database = Room.databaseBuilder(getApplicationContext(),       RoomDemoDatabase.class, "database_name")        .build();

生成數據庫實例的其他操作

Room.databaseBuilder(getApplicationContext(),            RoomDemoDatabase.class, "database_name")            .addCallback(new RoomDatabase.Callback() {              //第一次創建數據庫時調用,但是在創建所有表之后調用的              @Override              public void onCreate(@NonNull SupportSQLiteDatabase db) {                super.onCreate(db);              }              //當數據庫被打開時調用              @Override              public void onOpen(@NonNull SupportSQLiteDatabase db) {                super.onOpen(db);              }            })            .allowMainThreadQueries()//允許在主線程查詢數據            .addMigrations()//遷移數據庫使用,下面會單獨拿出來講            .fallbackToDestructiveMigration()//遷移數據庫如果發生錯誤,將會重新創建數據庫,而不是發生崩潰            .build();

數據庫遷移(升級)

Room.databaseBuilder(getApplicationContext(), MyDb.class, "database-name")    .addMigrations(MIGRATION_1_2, MIGRATION_2_3).build();static final Migration MIGRATION_1_2 = new Migration(1, 2) {  @Override  public void migrate(SupportSQLiteDatabase database) {    database.execSQL("CREATE TABLE `Fruit` (`id` INTEGER, "        + "`name` TEXT, PRIMARY KEY(`id`))");  }};static final Migration MIGRATION_2_3 = new Migration(2, 3) {  @Override  public void migrate(SupportSQLiteDatabase database) {    database.execSQL("ALTER TABLE Book "        + " ADD COLUMN pub_year INTEGER");  }};

 

創建嵌套對象

有時,您希望將一個實體或普通的以前的Java對象(POJO)作為數據庫邏輯中的一個完整的整體來表示,即使該對象包含幾個字段。在這些情況下,您可以使用@Embedded來表示一個對象,您希望將其分解為表中的子字段。然后可以像對其他單個列一樣查詢嵌入式字段

class Address {  public String street;  public String state;  public String city;  @ColumnInfo(name = "post_code")  public int postCode;}@Entityclass User {  @PrimaryKey  public int id;  public String firstName;  @Embedded  public Address address;}

這樣user表中的字段就包含了 id , firstName , street , state , city , 和 post_code

注意 :嵌入式字段還可以包含其他嵌入式字段

如果一個實體具有相同類型的多個內嵌字段,則可以通過設置前綴屬性(prefix)使每個列保持惟一。然后將所提供的值添加到嵌入對象中每個列名的開頭

 @Embedded(prefix = "foo_") Coordinates coordinates;

和 LiveData 一起使用

添加依賴

// ReactiveStreams support for LiveDataimplementation "android.arch.lifecycle:reactivestreams:1.0.0"

修改返回類型

@Daopublic interface MyDao {  @Query("SELECT first_name, last_name FROM user WHERE region IN (:regions)")  public LiveData<List<User>> loadUsersFromRegionsSync(List<String> regions);}

和RxJava一起使用

添加依賴

// RxJava support for Roomimplementation "android.arch.persistence.room:rxjava2:1.0.0"

修改返回類型

@Daopublic interface MyDao {  @Query("SELECT * from user where id = :id LIMIT 1")  public Flowable<User> loadUserById(int id);}

直接游標訪問

@Daopublic interface MyDao {  @Query("SELECT * FROM user WHERE age > :minAge LIMIT 5")  public Cursor loadRawUsersOlderThan(int minAge);}

類型轉換

定義轉換類,@TypeConverter注解定義轉換的方法

public class Converters {  @TypeConverter  public static Date fromTimestamp(Long value) {    return value == null ? null : new Date(value);  }  @TypeConverter  public static Long dateToTimestamp(Date date) {    return date == null ? null : date.getTime();  }}

@TypeConverters注解,告知數據庫要依賴哪些轉換類

@Database(entities = {User.class}, version = 1)@TypeConverters({Converters.class})public abstract class AppDatabase extends RoomDatabase {  public abstract UserDao userDao();}

使用這些轉換器,您可以在其他查詢中使用您的自定義類型,正如您將使用基本類型一樣,如下代碼所示

@Entitypublic class User {  ...  private Date birthday;}@Daopublic interface UserDao {  ...  @Query("SELECT * FROM user WHERE birthday BETWEEN :from AND :to")  List<User> findUsersBornBetweenDates(Date from, Date to);}

輸出模式

在編譯時,將數據庫的模式信息導出到JSON文件中,這樣可有利于我們更好的調試和排錯

build.gradleandroid {  ...  defaultConfig {    ...    javaCompileOptions {      annotationProcessorOptions {        arguments = ["room.schemaLocation":               "$projectDir/schemas".toString()]      }    }  }}

您應該將導出的JSON文件(表示數據庫的模式歷史記錄)存儲在您的版本控制系統中,因為它允許為測試目的創建您的數據庫的舊版本

總結

以上所述是小編給大家介紹的Android架構組件Room的使用詳解,希望對大家有所幫助,如果大家有任何疑問請給我留言,小編會及時回復大家的。在此也非常感謝大家對VEVB武林網網站的支持!


注:相關教程知識閱讀請移步到Android開發頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 阳西县| 福州市| 司法| 荣成市| 玉田县| 江永县| 高清| 苏尼特右旗| 仙居县| 郓城县| 蒙城县| 蛟河市| 吉林省| 永泰县| 绥江县| 色达县| 巢湖市| 会同县| 汨罗市| 大英县| 公安县| 长海县| 中西区| 蕉岭县| 抚宁县| 瑞金市| 青铜峡市| 本溪| 璧山县| 交城县| 通河县| 盐边县| 龙山县| 寻乌县| 宿州市| 四平市| 武义县| 博客| 赣州市| 紫金县| 崇信县|