Android数据库之GreenDao应用分析

一、前言

最近看了一篇关于GreenDao的文章 ,感觉使用这个操作数据库还是很好用的,帮我们省了不少的查询代码。以前用过原生的SQLite数据库,但是需要自己封装,自己写SQL语句,仔细找了一下发现 Android 平台上的数据库框架可真不少,但是有一个共同特点就是基于对象关系映射模型的。实现的目标也都是不需要写 SQL 语句,通过对对象的操作保存和操作数据。要是从语法的简洁性来说都有自己的特点,总的来说不相上下。

  • OrmLite 基于反射,缺少中文文档
  • GreenDao,资料多,支持加密
  • Realm,跨平台,支持加密

二、GreenDao介绍

GreenDao是Greenrobot公司的产品,这个公司的另一个非常成功的框架是EventBus,是一个很好的“订阅/发布”的事件处理框架。通过 GreenDao,我们可以更快速的操作数据库,我们可以使用简单的面相对象的API来存储,更新,删除和查询 Java 对象。

GreenDao是一个开源的安卓ORM框架,能够使SQLite数据库的开发再次变得有趣。它减轻开发人员处理低级数据库需求,同时节省开发时间。SQLite是一个令人敬畏的内嵌的关系数据库,编写SQL和解析查询结果是相当乏味和耗时的任务。通过将Java对象映射到数据库表(称为ORM,“对象/关系映射”),GreenDao可以将它们从这些映射中释放出来,这样,您可以使用简单的面向对象的API来存储,更新,删除和查询数据库。在性能方面,GreenDao 针对 Android 进行了高度优化,最小的内存开销、依赖体积小 同时还是支持数据库加密。

简单的讲,GreenDao是一个将对象映射到 SQLite 数据库中的轻量且快速的 ORM 解决方案。



GreenDao数据库的特点:

  • 存取速度快
  • 支持数据库加密
  • 轻量级( < 150K)
  • 激活实体
  • 支持缓存
  • 代码自动生成

总之,效率很高,插入和更新的速度比SQLite快。

GreenDao优缺点:

  • 优点:效率很高,在增、改、查方面都比其他框架快出一大截,尤其是查询。这是因为,GreenDao本身底层使用的不是反射,而是有一个Java工程来专门生成必要的代码
  • 缺点:GreenDao的缺点是学习成本高。这个框架不像ORMLite那样简单易上手,使用GreenDao之前需要配置一大堆参数,即它封装的不是很完整

下面是GreenDao官网上的一张图,将GreenDao的各方面与其他的框架做比较:



官网地址 :http://greenrobot.org/greendao/

GitHub : GreenDao

三、GreenDao应用

3.1 依赖库加载

在工程的根目录下的build.gradle文件中添加:

buildscript {
    repositories {
        jcenter()
        mavenCentral() // add repository
    }
    dependencies {
        classpath 'com.android.tools.build:gradle:3.1.1'
        classpath 'org.greenrobot:greendao-gradle-plugin:3.2.2' // add plugin
    }
}

在项目的.gradle文件里面添加:

apply plugin: 'com.android.application'
apply plugin: 'org.greenrobot.greendao' // apply plugin

dependencies {
    implementation 'org.greenrobot:greendao:3.2.2' // add library
}

3.2 解锁技能

对greendao的generator生成文件进行配置,在项目的.gradle文件里面添加:

greendao {
    schemaVersion 1
    daoPackage '生成文件包名' // 一般为app包名+生成文件的文件夹名
    targetGenDir 'src/main/java'
}

greendao配置元素支持多种配置选项:

  • schemaVersion:指定数据库schema版本号,迁移等操作会用到
  • daoPackage:通过gradle插件生成的数据库相关文件的包名,默认为你的entity所在的包名
  • targetGenDir:自定义生成数据库文件的目录,可以将生成的文件放到我们的java目录中,而不是build中,这样就不用额外的设置资源目录了

3.3 创建实体类

生成dao文件

@Entity
public class Meizi {

    @Id(autoincrement = true)
    private Long _id;
    private String source;
    @NotNull
    private String url;
}


几个注解含义:

  •  @Entity:将我们的java普通类变为一个能够被greenDAO识别的数据库类型的实体类
  •  @nameInDb:在数据库中的名字,如不写则为实体中类名
  •  @Id:选择一个long / Long属性作为实体ID。 在数据库方面,它是主键。 参数autoincrement是设置ID值自增
  •  @NotNull:使该属性在数据库端成为“NOT NULL”列。 通常使用@NotNull标记原始类型(long,int,short,byte)是有意义的
  •  @Transient:表明这个字段不会被写入数据库,只是作为一个普通的java类字段,用来临时存储数据的,不会被持久化

注意:编写完实体类以后在实体类界面下按下Ctrl+F9(Make project),程序会自动编译生成dao文件,生成的文件一共有三个。这里要解释一下生成的三个核心类的作用:



  • DaoMaster:使用greenDAO的切入点。DaoMaster保存数据库对象(SQLiteDatabase)并管理特定模式的DAO类(而不是对象)。它具有静态方法来创建表或将它们删除。 其内部类OpenHelper和DevOpenHelper是在SQLite数据库中创建模式的SQLiteOpenHelper实现。一个DaoMaster就代表着一个数据库的连接
  • DaoSession:管理特定模式的所有可用DAO对象,您可以使用其中一个getter方法获取。 DaoSession还为实体提供了一些通用的持久性方法,如插入,加载,更新,刷新和删除DaoSession可以让我们使用一些Entity的基本操作和获取Dao操作类,DaoSession可以创建多个,每一个都是属于同一个数据库连接的
  • XxxDAO:数据访问对象(DAO)持续存在并查询实体。 对于每个实体,GreenDAO生成一个DAO。 它比DaoSession有更多的持久化方法,例如:count,loadAll和insertInTx

3.4 使用Greendao

创建一个application类,在application中完成DaoSession的初始化,避免以后重复初始化,便于使用。

public class MyApplication extends Application {   
    private DaoMaster.DevOpenHelper mHelper;   
    private SQLiteDatabase db;   
    private DaoMaster mDaoMaster;   
    private DaoSession mDaoSession;
    //静态单例
    public static MyApplication instances;
     @Override
    public void onCreate() {
         super.onCreate();
         instances = this;
         setDatabase();
     }

     public static MyApplication getInstances(){
         return instances;
     }

     /**     * 设置greenDao     */
     private void setDatabase() {
         // 通过 DaoMaster 的内部类 DevOpenHelper,你可以得到一个便利的 SQLiteOpenHelper 对象
         // 可能你已经注意到了,你并不需要去编写「CREATE TABLE」这样的 SQL 语句,因为 greenDAO 已经帮你做了
         // 注意:默认的 DaoMaster.DevOpenHelper 会在数据库升级时,删除所有的表,意味着这将导致数据的丢失
         // 所以,在正式的项目中,你还应该做一层封装,来实现数据库的安全升级。
         mHelper = new DaoMaster.DevOpenHelper(this, "sport-db", null);
         db = mHelper.getWritableDatabase();
         // 注意:该数据库连接属于 DaoMaster,所以多个 Session 指的是相同的数据库连接。
         mDaoMaster = new DaoMaster(db);
         mDaoSession = mDaoMaster.newSession();
     }    

    public DaoSession getDaoSession() {
         return mDaoSession;
    }

    public SQLiteDatabase getDb() {
         return db;
     }
}

Greendao操作数据库文件(增,删,改,查)

    /**     * 增     */
    public void insert(){
        String date = new Date().toString();
        mDayStep = new dayStep(null,date,0);//第一个是id值,因为是自增长所以不用传入
        dao.insert(mDayStep);
    }

    /**     * 查     */
    public void Search(){
        //方法一
        List<dayStep> mDayStep = dao.loadAll();

        //方法二
        List<dayStep> mDayStep = dao.queryBuilder().list();

        //方法三 惰性加载
        //List<dayStep> mDayStep = dao.queryBuilder().listLazy();
        for (int i = 0; i < mDayStep.size(); i++) {
            String date = "";
            date = mDayStep.get(i).getDate();
            Log.d("cc", "id:  "+i+"date:  "+date);
        }
    }

    /*** 删 * @param i 删除数据的id     */
    public void delete(long i){
        dao.deleteByKey(i);
        //当然Greendao还提供了其他的删除方法,只是传值不同而已
    }

    /** *改     * @param i     * @param date     */
    public void correct(long i,String date)    {
        mDayStep = new dayStep((long) i,date,0);
        dao.update(mDayStep);
    }

    /**     *修改或者替换(有的话就修改,没有则替换)     */
    public void insertOrReplace(long i,String date){
        mDayStep = new dayStep((long) i,date,0);
        dao.insertOrReplace(mDayStep);
    }

    /**     *查找符合某一字段的所有元素     */
    public void searchEveryWhere(String str){
        List<dayStep> mList = dao.queryBuilder().where(dao.date.eq(str)).build().listLazy();
        List<dayStep> mList = dao.queryBuilder().where(dao.date.eq(str)).build().listLazy();
    }

四、SQL语句

重温SQL语句:

4.1 查询数据

 select * from table1 where 范围;

4.2 插入数据

insert into table1(field1,field2) values(value1,value2);

4.3 删除数据

delete from table1 where 范围;

4.4 更新数据

update table1 set field1=value1, field2=value2 where 范围;

4.5 模糊查询

 select * from table1 where field1 like ’%value1%’;

4.6 排序

 select * from table1 order by field1,field2 [desc];

4.7 分页查询(limit 要放到最后)

 select * from table1 where 范围 limit 0,10;

4.8 求总数

 select count as totalcount from table1;

4.9 求和

select sum(field1) as sumvalue from table1;

4.10 求平均数

 select avg(field1) as avgvalue from table1;

4.11 求最大

 select max(field1) as maxvalue from table;

4.12 求最小

 select min(field1) as minvalue from table1;

五、总结

这里主要介绍GreenDao 3.0使用注解的情况,以及实现了简单的增删改查,过了一遍GreenDao主要功能,还有些高级特性用到再研究吧。纵观下来,GreenDAO还是挺简单的,但也很实用,简化了数据库调用的复杂度,具体的执行就交给原生的Android数据库管理类。

其实呢,干我们这行,啥时候懈怠,就意味着长进的停止,长进的停止就意味着被淘汰,只能往前冲,直到凤凰涅槃的一天!


参考