Orm(对象关系模型)
- OrmLite框架介绍
- 对比主流的Orm框架
- OrmLite基本用法
一、OrmLite 框架介绍:
Ormlite 框架是第三方对数据库操作的封装的一个框架,为了提高开发效率,尤其是对某些 数据库操作特别频繁的 app,建议使用 OrmLite 框架。它是一个非常轻量级的数据库操作框架, 它的底层是根据反射机制来实现的。
Why OrmLite?
-
大多数Android应用需要使用SQLite数据库
-
对数据库进行操作需要编写大量的代码
-
类似于JavaEE中的Hibernate框架,Android中也有很多第三方 框架来简化数据持久化操作
-
常用ORM框架有:
– OrmLite 使用注解,使用简单
– GreenDAO自动生成代码,性能高 – SugarORM
– Active Android
– Realm
二、OrmLite 框架使用步骤:
OrmLite使用步骤(简洁版)
1.在 http://ormlite.com/releases/官网下载 ormlite-android-5.1jar 和 ormlite-core-5.1.jar 两 jar 包 。
2.将两个jar包放到工程的libs文件夹里面,然后全部选中,右键点击 add As Library 添加到库里面(Mac版的可以在Project Structure中的Dependencies中添加jar包不用下载)
build.gradle添加以下依赖
implementation 'com.j256.ormlite:ormlite-core:5.1'
implementation 'com.j256.ormlite:ormlite-android:5.1'
3.定义实体类,使用OrmLite注解定义表和字段
创建相应的 javaBean,使用注解的方式:
在类名前添加
@DatabaseTable()注解:定义数据库表的名称
分别在属性上添加
@DatabaseField(columnName= “name”) ,columnName 的值为该字段在数据中的列名,
@DatabaseField(generatedId = true) ,generatedId 表示 id 为主键且自动生成。
Student,java 实体类
import com.j256.ormlite.field.DataType;
import com.j256.ormlite.field.DatabaseField;
import com.j256.ormlite.table.DatabaseTable;
/**
* 学生信息的属性封装类
*/
//定义会生成数据库的的表名
@DatabaseTable(tableName = "tb_student")
public class Student {
//参数1generatedId 表示 id 为主键且自动生成。
@DatabaseField(generatedId = true)
private int id;
//参数1:列的名称 ,参数2:数据类型 参数3:是否为空
@DatabaseField(columnName = "name", dataType = DataType.STRING, canBeNull = true,)
private String name;
//可以不设置,默认列名是 定义的属性名 age
@DatabaseField
private int age;
@DatabaseField
private String phone;
public Student() {
}
public Student(String name, int age, String phone) {
this.name = name;
this.age = age;
this.phone = phone;
}
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;
}
public String getPhone() {
return phone;
}
public void setPhone(String phone) {
this.phone = phone;
}
@Override
public String toString() {
return "Student{" +
"id=" + id +
", name='" + name + '\'' +
", age=" + age +
", phone='" + phone + '\'' +
'}';
}
}
4.继承OrmLiteSqliteOpenHelper类(相当于SQLite数据库的帮助类)
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import com.demo.ormlitedemo.bean.Student;
import com.j256.ormlite.android.apptools.OrmLiteSqliteOpenHelper;
import com.j256.ormlite.support.ConnectionSource;
import com.j256.ormlite.table.TableUtils;
import java.sql.SQLException;
/**
* 数据库帮助类 ,单例模式
*/
public class DatabaseHelper extends OrmLiteSqliteOpenHelper {
//1.私有构造函数
private DatabaseHelper(Context context) {
//参数1:上下文 参数2:数据库的名称 参数3:游标 参数4 数据库的版本
super(context, "test.db", null, 1);
}
//2.私有静态的对象
private static DatabaseHelper sHeler = null;
//3.共有静态的获取对象实例的方法
public static synchronized DatabaseHelper getInstance(Context context) {
if (sHeler == null) {
sHeler = new DatabaseHelper(context);
}
return sHeler;
}
@Override
public void onCreate(SQLiteDatabase database, ConnectionSource connectionSource) {
//建表的方法
try {
//参数1:连接资源 参数2:定义好的实体类
TableUtils.clearTable(connectionSource, Student.class);
} catch (SQLException e) {
e.printStackTrace();
}
//如果再建表,可以通过上面的方法,在写一个实体类就行了
}
//升级数据库的方法
@Override
public void onUpgrade(SQLiteDatabase database, ConnectionSource connectionSource, int oldVersion, int newVersion) {
//1如果数据库升级,要先删除之前的表
try {
//参数1:连接资源,参数2:实体类 参数3:忽略错误
TableUtils.dropTable(connectionSource, Student.class, true)
//2.重新执行oncreate
onCreate(database, connectionSource);
} catch (SQLException e) {
e.printStackTrace();
}
}
}
5.获得对应表的Dao类(数据操作类)
StudentDao.java
import android.content.Context;
import android.util.Log;
import com.demo.ormlitedemo.bean.Student;
import com.demo.ormlitedemo.db.DatabaseHelper;
import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.stmt.UpdateBuilder;
import java.sql.SQLException;
import java.util.List;
public class StudentDao {
Context context;
public StudentDao(Context context) {
this.context = context;
}
//拿Hepler对象
public DatabaseHelper getHelper() {
return DatabaseHelper.getInstance(context);
}
//StudentDao对象
public Dao<Student, Integer> getStudentDao() throws SQLException {
//传入实体类拿到这个实体类的Dao对象
return getHelper().getDao(Student.class);
}
//插入数据操作
public void testInsert() throws SQLException {
Dao<Student, Integer> stuDao = getStudentDao();
Student stu1 = new Student("测试1", 21, "666");
Student stu2 = new Student("测试2", 22, "666");
Student stu3 = new Student("测试3", 23, "666");
stuDao.create(stu1);
stuDao.create(stu2);
stuDao.create(stu3);
}
//查询操作
public void testQuery() throws SQLException {
Dao<Student, Integer> stuDao = getStudentDao();
//查询所有数据
List<Student> students = stuDao.queryForAll();
for (Student student : students) {
Log.e("TAG", "查询所有" + student.toString());
}
//按id查询
Student stu = stuDao.queryForId(3);
Log.e("TAG", "按id查询" + stu.toString());
//条件查询
students = stuDao.queryForEq("age", "21");
for (Student student : students) {
Log.e("TAG", "条件查询" + student.toString());
}
}
//更新操作
public void testUpdate() throws SQLException {
Dao<Student, Integer> stuDao = getStudentDao();
//更新构造器
UpdateBuilder update = stuDao.updateBuilder();
//设置更新条件 eq是具体条件值 and 是且的意思 gt() GREATER THAN 是年龄要大于22
update.setWhere(update.where().eq("phone", "666").and().gt("age", 22));
//更新值
update.updateColumnValue("name", "测试更新————");
update.updateColumnValue("phone", "110");
update.update();
//也可以直接使用sql语句
stuDao.updateRaw("update tb_student set name='测试更新————',phone='110' where id=?", "1");
}
//删除操作
public void testDelete() throws SQLException {
Dao<Student, Integer> stuDao = getStudentDao();
stuDao.deleteById(1);
}
}
6.执行增删改查操作
MainActivity.java
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import com.demo.ormlitedemo.dao.StudentDao;
import java.sql.SQLException;
public class MainActivity extends AppCompatActivity {
private StudentDao stuDao;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
stuDao = new StudentDao(this);
try {
//执行插入操作
// stuDao.testInsert();
//执行查询操作
stuDao.testQuery();
stuDao.testUpdate();
stuDao.testQuery();
stuDao.testDelete();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
ormLite实现表一对多
一个学校对应多个学生
在bean类中添加一个School.java
/**
* 学校的属性封装
*/
//创建学校表
@DatabaseTable(tableName = "tb_school")
public class School {
@DatabaseField(generatedId = true)
private int id;
@DatabaseField
private String name;
@DatabaseField
private String location;
@ForeignCollectionField//外键集合的字段
private Collection<Student> students;
public School(String name, String location) {
this.name = name;
this.location = location;
}
public School() {
}
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 String getLocation() {
return location;
}
public void setLocation(String location) {
this.location = location;
}
public Collection<Student> getStudents() {
return students;
}
public void setStudents(Collection<Student> students) {
this.students = students;
}
@Override
public String toString() {
return "School{" +
"id=" + id +
", name='" + name + '\'' +
", location='" + location + '\'' +
", students=" + students +
'}';
}
}
学生类也做稍微修改:
import com.j256.ormlite.field.DataType;
import com.j256.ormlite.field.DatabaseField;
import com.j256.ormlite.table.DatabaseTable;
/**
* 学生信息的属性封装类
*/
@DatabaseTable(tableName = "tb_student")
public class Student {
//参数1generatedId 表示 id 为主键且自动生成。
@DatabaseField(generatedId = true)
private int id;
//参数1:列的名称 ,参数2:数据类型 参数3:是否为空
@DatabaseField(columnName = "name", dataType = DataType.STRING, canBeNull = true)
private String name;
//可以不设置,默认列名是 定义的属性名 age
@DatabaseField
private int age;
@DatabaseField
private String phone;
//学生所在的学校 参数1:列数属性名 参数2:设置外键 参数3:学校信息的自动刷新 学生是多,加外键
@DatabaseField(columnName = "school_id", foreign = true, foreignAutoRefresh = true)
private School school;
public Student() {
}
public Student(String name, int age, String phone, School school) {
this.name = name;
this.age = age;
this.phone = phone;
this.school = school;
}
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;
}
public String getPhone() {
return phone;
}
public void setPhone(String phone) {
this.phone = phone;
}
public School getSchool() {
return school;
}
public void setSchool(School school) {
this.school = school;
}
@Override
public String toString() {
return "Student{" +
"id=" + id +
", name='" + name + '\'' +
", age=" + age +
", phone='" + phone + '\'' +
'}';
}
}
Helper类多建一张表
TableUtils.createTable(connectionSource, Student.class);
TableUtils.createTable(connectionSource, School.class);
Dao类的插入和查询
//插入数据操作
public void testInsert() throws SQLException {
Dao<Student, Integer> stuDao = getStudentDao();
Dao<School, Integer> schDao = getSchoolDao();
School school = new School("北京大学", "北京");
Student stu1 = new Student("测试1", 21, "666", school);
Student stu2 = new Student("测试2", 22, "666", school);
Student stu3 = new Student("测试3", 23, "666", school);
schDao.create(school);
stuDao.create(stu1);
stuDao.create(stu2);
stuDao.create(stu3);
}
//查询操作
public void testQuery() throws SQLException {
Dao<Student, Integer> stuDao = getStudentDao();
//查询所有数据
List<Student> students = stuDao.queryForAll();
for (Student student : students) {
Log.e("TAG", "查询所有学生信息" + student.toString() + student.getSchool());
}
//查询学校
Dao<School, Integer> schDao = getSchoolDao();
List<School> schools = schDao.queryForAll();
for (School school : schools) {
Log.e("TAG", "查询学校信息" + school.toString());
for (Student student : school.getStudents()) {
Log.e("TAG", "查询学校学生的" + student.toString());
}
}
// //按id查询
// Student stu = stuDao.queryForId(3);
// Log.e("TAG", "按id查询" + stu.toString());
// //条件查询
// students = stuDao.queryForEq("age", "21");
// for (Student student : students) {
// Log.e("TAG", "条件查询" + student.toString());
// }
}
事务,如果其中出现任何一条数据抛出异常,此时插入将不成功!
如果要同时添加或者删除多条数据可以采用事务来解决大大提升效率
/**
* 测试事务操作
* @throws SQLException
*/
public void testTransactions() throws SQLException {
TransactionManager.callInTransaction(
getDatabaseHelper().getConnectionSource(),
new Callable<Void>() {
@Override
public Void call() throws Exception {
Student stu = new Student("trans test", new Random().nextInt(20), "...",null);
Dao stuDao = getStuDAO();
for (int i = 0; i < 5; i++) {
stuDao.create(stu);
if (i == 2) {
throw new SQLException("test.....");
}
}
return null;
}
}
);
}