Android jetpack Room數據庫(三)複雜數據存取

注:基本使用可結合Android jetpack Room數據庫(一)基本使用 去看

1.對象包含單個對象

1.1.直接用@Embedded

作用:將裏面對象的屬性當成列嵌入到外層對象生成的表中

 

注意:兩個對象中如果存在相同的名稱,需要用@ColumnInfo註解重新定義列名或者用@Embedded(prefix = "department")增加前綴,保證列名不重複。否則會報錯:

錯誤: Multiple fields have the same columnName: id. Field names: id, department > id.

1.1.1.看一下Department的定義

public class Department {
    @ColumnInfo(name = "departmentId")
    public int id;
    @ColumnInfo(name = "departmentName")
    public String name;
​
    public Department() {
    }
​
    @Ignore
    public Department(int id, String name) {
        this.id = id;
        this.name = name;
    }
}

1.1.2.然後插入數據,插入的數據內容如下

{"department":{"id":1,"name":"公司領導"},"id":1,"userAge":10,"userName":"user001"}

1.1.3.看一下數據庫:

 

OK,可以看到已經成功完成對象嵌套對象的數據類型數據庫插入。

1.1.4.咱們再將數據取出來看看是不是原來的格式,

new Thread(new Runnable() {
                @Override
                public void run() {
                    String name=dataBinding.etName.getText().toString().trim();
                    User user=AppDataBase.getInstance(MainActivity.this).userDao().getUserInfoByName(name);
​
                    Log.e("database userGet  ",GsonUtils.toString(user));
                }
            }).start();

看到如下,和存入時一模一樣:

 

1.2.用TypeConverters轉換

作用:將對象轉爲字符串當成一個字段存在表中.

1.2.1.定義Department的轉換類,如下:

public class DepartmentConvert {
    @TypeConverter
    public Department revert(String jsonString) {
        // 使用Gson方法把json格式的string轉成T
        try {
​
            Type type = new TypeToken<Department>(){}.getType();
            Department data = new Gson().fromJson(jsonString,type);
            return data;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }
​
    @TypeConverter
    public String converter(Department data) {
        // 使用Gson方法把 T 轉成json格式的string,便於我們用的解析
        return new Gson().toJson(data);
    }
}

1.2.2.在咱們的user類上面加上TypeConverters註解

告訴room遇到對應的字段怎麼存取,注意department字段不需要再做任何操作

@Entity(tableName = "user",ignoredColumns = {"testField1"})  //實體類創建需要加上@Entity註解
@TypeConverters({DepartmentConvert.class})
public class User {
​
    @PrimaryKey @NonNull
    public int id;
    @ColumnInfo(name = "user_name")
    public String userName;
    @ColumnInfo(name = "user_age")
    public int userAge;
    @ColumnInfo(name = "user_mobile")
    public String userMobile;
​
    /**
     * 只是單個對象,不是List/set
     * 直接用@Embedded 嵌入到user表中,即user表中的列將根據Department的屬性增加
     */
//    @Embedded
//    public Department department;
​
    public Department department;
   
    。。。
    
    }

1.2.3.插入數據

{"department":{"id":1,"name":"公司領導"},"id":1,"userAge":10,"userName":"user001"}

1.2.4.查看一下數據表,已經將department字段轉成字符串存在department列了,如圖:

 

1.2.5.再通過名稱查出數據看看,如圖:

 

OK,也一樣的能成功的取出和存入時一樣的數據.

注意:Convert類不能提取成基類,否則在存的時候沒問題,取的時候會報錯:

java.lang.ClassCastException: com.google.gson.internal.LinkedTreeMap cannot be cast to com.example.paramtest.roomTest.entities.Department

錯誤示範:

public class BaseDataCovert<T> {
    @TypeConverter
    public T revert(String jsonString) {
        // 使用Gson方法把json格式的string轉成T
        try {

            Type type = new TypeToken<T>(){}.getType();
            T data = new Gson().fromJson(jsonString,type);
//            T data = GsonUtils.fromLocalJson(jsonString,type);
            return data;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    @TypeConverter
    public String converter(T data) {
        // 使用Gson方法把 T 轉成json格式的string,便於我們用的解析
        return new Gson().toJson(data);
    }
}


//只需要繼承自咱們定義的BaseDataCovert類,這不行 
public class DepartmentConvert extends BaseDataCovert<Department> { 

​ }     

       

 

2.對象包含一個對象的集合<List>

內容如下,對象中包含集合:

@Entity(tableName = "user", ignoredColumns = {"testField1"})  //實體類創建需要加上@Entity註解
public class User {
​
    @PrimaryKey
    @NonNull
    public int id;
    @ColumnInfo(name = "user_name")
    public String userName;
    @ColumnInfo(name = "user_age")
    public int userAge;
    @ColumnInfo(name = "user_mobile")
    public String userMobile;
​
    /**
     * 只是單個對象,不是List/set
     * 直接用@Embedded 嵌入到user表中,即user表中的列將根據Department的屬性增加
     */
//    @Embedded
//    public Department department;
​
//    public Department department;
​
    //對象中含有集合
    public List<Department> departments;
​
    public String testField1;
    
    。。。
    
    }

2.1.用convert直接存

2.1.1.新建一個轉list的Convert基類

public class BaseListConvert<T> {
    @TypeConverter
    public  List<T> revert(String jsonString) {
        // 使用Gson方法把json格式的string轉成List
        try {
​
            Type type = new TypeToken<ArrayList<T>>(){}.getType();
            List<T> list = new Gson().fromJson(jsonString,type);
            return list;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }
​
    @TypeConverter
    public String converter(List<T> list) {
        // 使用Gson方法把List轉成json格式的string,便於我們用的解析
        return new Gson().toJson(list);
    }
​
}

2.1.2.新建轉ListDepartment的convert類

//直接集成自BaseListConvert,將類型傳進去就行了
public class DepartmentListConvert extends BaseListConvert<Department> {
​
}

2.1.3.在user類增加TypeConverters

 

2.1.4.向數據庫插入數據

{"departments":[{"id":1,"name":"公司領導"},{"id":2,"name":"軟件部"}],"id":1,"userAge":10,"userName":"user001"}

2.1.5.查看數據庫是否成功插入數據

已經將list字段成功插入到數據庫

 

2.1.6.通過名稱user001將數據查出來看一下

成功查詢出和原始數據一樣的數據

 

2.2.通過relation進行數據存取

複雜且已經有以上替換方案,略,後續有時間再補

2.3.通過ForeignKey進行關聯存取

複雜且已經有以上替換方案,略,後續有時間再補

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章