實現一個通過物件對映到Android資料庫框架
阿新 • • 發佈:2020-12-28
學習目標:
實現一個通過物件class對映到Android資料庫框架
學習內容:
- 1.物件關係對映型(ORM)模式
ORM(Object-Relational Mapping)表示物件關係對映.在面向物件的軟體開發中,通過ORM,就可以把物件對映到關係型資料庫中.只要有一套程式能夠做到加你物件與資料庫的關聯,操作物件就可以直接操作資料庫資料,就可以說這套程式實現了ORM物件關係對映,將物件對映成資料表中的一條條記錄。
比如,我們有這樣一個物件類
package com.suyong.mydatabase;
public class User {
private String account;
private String pasword;
public User(String account, String pasword) {
this.account = account;
this.pasword = pasword;
}
public String getAccount() {
return account;
}
public void setAccount(String account) {
this .account = account;
}
public String getPasword() {
return pasword;
}
public void setPasword(String pasword) {
this.pasword = pasword;
}
}
會根據這個表和裡面的成員變數生成一個相對應的表。但如果我們不想把這個class的所有成員變數都發給到資料庫表裡,但這個方式是不行的,所以ORM模式:
- 優點:方便快捷,不需要其他複雜的處理
- 缺點:無法確定類物件中到底有哪些成員變數不需要建立表字段
所以我們下面來通過另一種方式,我們通過註解加反射的方式,來指定class中要建立的表字段。如下這種:
package com.suyong.mydatabase;
public class User {
@Field
private String account;
private String pasword;
public User(String account, String pasword) {
this.account = account;
this.pasword = pasword;
}
public String getAccount() {
return account;
}
public void setAccount(String account) {
this.account = account;
}
public String getPasword() {
return pasword;
}
public void setPasword(String pasword) {
this.pasword = pasword;
}
}
像上面這種,我們通過@Field註解標記我們要生成表字段的變數,這樣我們不標記的變數就不生成表字段了,那要怎麼實現?下面就來敲程式碼。
我們首先需要建立一個Android Library(mysqlite),用來實現資料庫的建立和載入。
//修飾需要存到資料庫裡的成員變數
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface NameField {
String name();
}
//修飾需要存放到資料庫裡的類
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
public @interface TableField {
String name();
}
package com.suyong.mysqlite;
import android.database.sqlite.SQLiteDatabase;
import java.io.File;
//資料庫工廠
public class BaseDaoFactory{
private String path;
private SQLiteDatabase sqLiteDatabase;
private static BaseDaoFactory instance = new BaseDaoFactory();
private BaseDaoFactory() {
}
public static BaseDaoFactory getInstance() {
return instance;
}
/**
* 初始化
*
* @param path 儲存位置和資料庫名字
* /data/data/包名/database/data.db
*/
public void init(String path) {
this.path = path;
File file = new File(this.path);
//建立父資料夾
if (!file.getParentFile().exists()) {
file.getParentFile().mkdirs();
}
//建立或開啟資料庫
sqLiteDatabase = SQLiteDatabase.openOrCreateDatabase(this.path, null);
}
//返回與clazz所對應的資料庫裡的表
public<T> BaseDAO<T> getBaseDao(Class<T> clazz) {
BaseDAO<T> baseDAO = new BaseDAO<T>();
baseDAO.init(clazz, sqLiteDatabase);
return baseDAO;
}
}
public interface IBaseDao <T>{
//插入資料
long insert(T data);
}
然後寫完上面的程式碼,我們就可以在app模組下優雅的呼叫。
package com.suyong.mydatabase;
import android.app.Application;
import com.suyong.mysqlite.BaseDaoFactory;
public class MyApplication extends Application {
@Override
public void onCreate() {
super.onCreate();
//初始化資料庫 不存在就建立
BaseDaoFactory.getInstance().init("data/data/com.suyong.mydatabase/database/data.db");
}
}
package com.suyong.mydatabase;
import com.suyong.mysqlite.NameField;
import com.suyong.mysqlite.TableField;
import java.sql.Time;
//這個就是我們要對映的實體類
@TableField(name="user")
public class User {
@NameField(name = "account")
private String account;
@NameField(name = "password")
private String password;
//這個成員變數沒有註解,所以不會對映到資料庫的表裡
private Time birthday;
public User(String account, String pasword) {
this.account = account;
this.password = pasword;
}
public String getAccount() {
return account;
}
public void setAccount(String account) {
this.account = account;
}
public String getPassword() {
return password;
}
public void setPassword(String pasword) {
this.password = pasword;
}
}
然後我們就只要寫出下面的兩行程式碼就可以向資料庫裡新增資料了。
//開始插入資料
public void insert(View view) {
BaseDAO<User> baseDao = BaseDaoFactory.getInstance().getBaseDao(User.class);
baseDao.insert(new User("1215","12132"));
}
這裡我就實現了插入的方法,其他的方法依葫蘆畫瓢就可以了,就不寫了,嘻嘻。
另:
如果我們要實現多使用者分表的話,我們可以在MyApplication裡的那句初始化資料庫的時候,判斷不同使用者使用不同建立的資料庫檔案就可以,比如下面的虛擬碼。
if(A使用者){
BaseDaoFactory.getInstance().init("data/data/com.suyong.mydatabase/database/data1.db");
}else if(B使用者){
BaseDaoFactory.getInstance().init("data/data/com.suyong.mydatabase/database/data2.db");
}