大致分为以下几个方面:

  1. 一些查询指令整理
  2. 使用SQL语句进行特殊查询
  3. 检测表字段是否存在
  4. 数据库升级
  5. 数据库表字段赋初始值

一、查询指令整理

1.链式执行的指令

return mDaoSession.getUserDao().queryBuilder().XXX.XXX.XXX.list();

一般的查询语句会在中间xxx的位置加上各种判断和过滤的方法指令,除了最后的终结指令list()或unique()返回的是集合或业务对象,其他的都是返回QueryBuilder对象,大多数情况下XXX的位置都是填上where语句,还有一些其他和sql关联的语句便于使用。

“whereOr” where语句里面写的条件都是用“且”连接,whereOr里的语句使用“或”连接

“distinct”  直接过滤掉重负字段

“limit”  分页n个一页,一般和offset结合使用

“offset” 忽略查询出的前n条结果

“orderAsc” 以字段升序排序

“orderDesc”以字段降序

“preferLocalizedStringOrder” 本地化字符串排序

“orderCustom” 自定义排序 里面需要传两个参数: 一个属性 和对应的排序方案 ASC 或是 DESC

“orderRaw”  也是自定义排序, 把字段和 排序方案 写在一个字符串传入

“stringOrderCollation” 也是自定义排序 可以合并多个升降排序方案 以日期升序 且 价格降序

2.条件里的指令

return mDaoSession.getUserDao().queryBuilder().where(UserDao.Properties.UserId.in(userIdList), UserDao.Properties.UserAge.eq(19)).list();

一个简单的where语句大概是这样,在where的括号里面可以并列的写很多条件,其中全部以“且” 来连接。除了上面的“in”和“eq”还有很多其他判断条件

“notEq” 和eq相反,别傻傻在再去外面敲“!”取反

“notIn” 同上

“or” 或者

“like” 就是sql语句的LIKE  "%"+string+"%"

“between” 也就是BETWEEN ? AND ?  可以取两个值的区间 (但是这条语句要慎用,不同的数据库不一样,有的是A<条件<B,有的是A<=条件<=B)

“gt” 相当于 >

“ge”相当于 >=

“lt” 相当于 <

“le”相当于  <=

“isNull” 为空

“notIsNull” 不为空

二、使用SQL语句进行特殊查询

一般遇到普通的增删改查操作无法轻易实现的功能,会使用这种rawQuery的方式。 我经常遇到的也就是两种场景:

1.使用SELECT DISTINCT

常用与一对多关系,假设图书馆现在有个“用户存书表” 有的用户有20本书,表里就会有20条他的数据,每条对应一本不同的书。

这时假设有个需求,查出这个表中,所有的用户名字,不许重复。 这时候用普通的查询指令就会非常麻烦了,需要使用SELECT DISTINCT指令查出某列名所有不重复的条目。

String queryString ="SELECT DISTINCT " + UserBookDao.Properties.UserName.columnName + " FROM " + UserBookDao.TABLENAME+ " ORDER BY "+ UserBookDao.Properties.CreatedTime+ " DESC "+ " LIMIT "+ page * LIMIT_NUM+ " , "+ LIMIT_NUM;ArrayList<String> result = new ArrayList<>();
Cursor c = mDaoSession.getDatabase().rawQuery(queryString,new String[]{});
try {if (c != null) {if (c.moveToFirst()) {do {result.add(c.getString(0));} while (c.moveToNext());}}
} finally {if (c != null) {c.close();}
}

大概代码的画风就是这个样子,先拼接出一个符合sql语法的字符串,上面也随机加了一写其他的操作指令字段排序和分页,使得查询指令看上去更加完整,然后使用游标来接收上面的查询结果。

可能大多数查询的时候会带上一些参数,比如where XX = XX 的过滤条件,假设有个需求需要在之前的查询用户需求上加上对出版社和图书价格的限制,则查询方式如下

String queryString ="SELECT DISTINCT " + UserBookDao.Properties.UserName.columnName + " FROM " + UserBookDao.TABLENAME // 董铂然博客园+ " WHERE "+ UserBookDao.Properties.Publisher.columnName + " = ?"+ " AND "+ UserBookDao.Properties.Price.columnName + " > ?"+ " ORDER BY "+ UserBookDao.Properties.CreatedTime+ " DESC ";ArrayList<String> result = new ArrayList<>();
Cursor c = mDaoSession.getDatabase().rawQuery(queryString, new String[]{"某出版社"),String.valueOf(100.00)});
try {if (c != null) {if (c.moveToFirst()) {do {result.add(c.getString(0));} while (c.moveToNext());}}
} finally {if (c != null) {c.close();}
}

带上参数的查询字符串需要在上面使用问号占位,然后在下面用rawQuery带参数的api里填上相关的入参。

2. SELECT同时查询多个字段

还是用这个查书的例子,假设一下要查“书名”、“出版社”、“价格” 三个字段

String queryString = "SELECT "+ UserBookDao.TABLENAME + "." + UserBookDao.Properties.BookName.columnName + ","+ UserBookDao.TABLENAME + "." + UserBookDao.Properties.Publisher.columnName + ","+ UserBookDao.TABLENAME + "." + UserBookDao.Properties.Price.columnName + " "+ "FROM "+ UserBookDao.TABLENAME + " "+ "WHERE"+ UserBookDao.Properties.Price + " > 100.00 ";
Cursor cursor = null;
try {cursor = session.getDatabase().rawQuery(queryString,new String[]{});if (cursor == null) {return payMap;}// 取出三个字段分别对应的索引,下面再对着索引去取值int nameIndex = cursor.getColumnIndex(UserBookDao.Properties.BookName.columnName);int publisherIndex = cursor.getColumnIndex(UserBookDao.Properties.Publisher.columnName);int priceIndex = cursor.getColumnIndex(UserBookDao.Properties.Price.columnName);if (nameIndex != -1 && publisherIndex != -1 && priceIndex != -1) {while (cursor.moveToNext()) {String name = cursor.getString(nameIndex);String publisher = cursor.getString(publisherIndex);Double price = cursor.getDouble(priceIndex);// 这里取到三个字段 自己是存模型还是字典 自己处理。}}
} finally {if (null != cursor) {cursor.close();}
}

下面可以一次性的取出三个所需字段进行使用,需要先得到字段对应索引,然后再对着索引取值。

三、检测表字段是否存在

private boolean hasColumn(SQLiteDatabase db, String tableName, String column) {if (TextUtils.isEmpty(tableName) || TextUtils.isEmpty(column)) {return false;}Cursor cursor = null;try {cursor = db.query(tableName, null, null, null, null, null, null);if (null != cursor && cursor.getColumnIndex(column) != -1) {return true;}} finally {if (null != cursor) {cursor.close();}}return false;
}

和上面取游标的方式类似,取出的列索引值如果不是-1,则代表能够取到这个字段返回true,否则和入参非法一起返回fasle。

四、数据库升级

这边会调用上面判断列名是否已经存在的方法。

然后重写父类的这个onUpgrade方法

private static class DemoOpenHelper extends DaoMaster.OpenHelper {public DemoOpenHelper(Context context, String name, SQLiteDatabase.CursorFactory factory) {super(context, name, factory);}@Overridepublic void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {// 数据库的版本控制 可以随着版本叠加不断增加差值if (oldVersion < 2) {if (!hasColumn(db, UserBookDao.TABLENAME, UserBookDao.Properties.Author.columnName)) {String sql = "alter table " + UserBookDao.TABLENAME +" add COLUMN " + UserBookDao.Properties.Author.columnName + " TEXT";db.execSQL(sql);}if (!hasColumn(db, UserBookDao.TABLENAME, UserBookDao.Properties.Type.columnName)) {String sql = "alter table " + UserBookDao.TABLENAME +" add COLUMN " + UserBookDao.Properties.Type.columnName + " INTEGER";db.execSQL(sql);}}}
}

除了上面的修改表,如果改动太多或是换了表明,还可以直接删了重建(这么做的话之前的数据也就删了)

if (oldVersion < 3) {UserDao.dropTable(new StandardDatabase(db),true);UserStudentDao.createTable(new StandardDatabase(db),true);
}

五、数据库表字段赋初始值

有些字段的初始值如果你不希望是0,或是空字符串,可以赋初始值。现在的赋值初始值就分为两种情况了

1.建表时附初始值

在3.0以前的版本 还是要写一个module,里面写类似代码来建表的

private static void addUser(Schema schema) {Entity user = schema.addEntity("User");user.addIdProperty();user.addStringProperty("name").notNull().defValue("\"jack\"");user.addStringProperty("address");user.addStringProperty("teacher");user.addIntProperty("age").primJavaType().defValue("17");
}

在3.0之后推行用注解和直接写Entity的写法,所以可以直接在Entity的类里指定

@Entity
public class Student {@Id(autoincrement = true)private long id; //主键private String name;private String schoolTime = "09-01"; //开学时间默认都是9月1日private int age = 19; // 刚上大学的默认都是19岁// 下面生成的getter 和setter省略 。。。
}

2.数据库升级时给升级字段赋初始值

上面说的的数据库升级,是需要写一条alter table的sql语句,可以直接拼接到这一行后面

// 上面判断该列名是否存在
// ...
String sql = "alter table " + UserBookDao.TABLENAME +" add COLUMN " + UserBookDao.Properties.Type.columnName + " INTEGER" + " NOT NULL DEFAULT(-1) "; // 直接拼接在语句最后 董铂然博客园
db.execSQL(sql);
// ...

注:以前听过一种说法是直接在UserDao这种生成的类里直接在生成的创建语句后面拼接DEFAULT,这里非常反对, 首先人家类名明确表明 // THIS CODE IS GENERATED BY greenDAO, DO NOT EDIT.  并且有些人的代码可能设置的是手动生成,但我们的项目就在gradle里设置了每次build都会先自动生成一下,这种情况每次都会覆盖。

以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,同时也希望多多支持脚本之家!

转自:http://www.jb51.net/article/101609.htm

转载于:https://www.cnblogs.com/YangBinChina/p/8417415.html

安卓GreenDao框架一些进阶用法整理(转)相关推荐

  1. Frida Hook Android App 进阶用法之 Java 运行时

    FridaHookAndroid 本文旨在覆盖使用 Frida 对 Android App 进行 hook 的绝大多数场景.文章提到的所有代码以及被测 App,详见:https://github.co ...

  2. 安卓从入门到进阶第九章(自动亮屏)

    安卓从入门到进阶第六章(dumpsys初探) 我希望文章是给出一个思路,让你能够跟着这个,找到框架,然后自行分析,总结,得到知识. 阅读代码,是需要长时间的训练,从问题出发,就跟从项目出发一样,在实战 ...

  3. android绑定交通卡,安卓手机公交卡的用法

    安卓手机公交卡的用法 近两年随着手机NFC的普及,移动支付逐渐火了起来,各个手机厂商纷纷推出自家的XX Pay移动钱包,手机刷公交地铁又遇到了春天.下面是小编收集整理的安卓手机公交卡的用法,欢迎阅读. ...

  4. pandas进阶用法(一)筛选条件、多重索引、缺失值

    一篇比较好的pandas指南,适合已经熟悉pandas,并想掌握一些进阶用法的读者,不适合对pandas完全不了解的新人.文章大部分是Stack Overflow常见问题集合. pandas 官网 原 ...

  5. 安卓表格框架-ExcelView

    转载请标明来源:安卓表格框架-ExcelView_分享+记录-CSDN博客 Github地址,欢迎star:https://github.com/September26/ExcelView 一.项目介 ...

  6. (数据科学学习手札61)xpath进阶用法

    一.简介 xpath作为对网页.对xml文件进行定位的工具,速度快,语法简洁明了,在网络爬虫解析内容的过程中起到很大的作用,除了xpath的基础用法之外(可参考我之前写的(数据科学学习手札50)基于P ...

  7. python orm框架sqlalchemy_python orm 框架中sqlalchemy用法实例详解

    本文实例讲述了python orm 框架中sqlalchemy用法.分享给大家供大家参考,具体如下: 一.ORM简介 1. ORM(Object-Relational Mapping,对象关系映射): ...

  8. Google Guava 库用法整理

    http://macrochen.iteye.com/blog/737058 参考: http://codemunchies.com/2009/10/beautiful-code-with-googl ...

  9. 如果要用thinkphp框架_php需要改哪些配置,thinkPHP框架动态配置用法实例分析

    本文实例讲述了thinkPHP框架动态配置用法.分享给大家供大家参考,具体如下: 最近在用@ThinkPHP 做系统的时候,要用到一个功能,就要动态的将系统的配置参数保存到Config文件中.以往,我 ...

最新文章

  1. SAP SD基础知识之信用控制范围
  2. 与内存对齐,字符数组求sizeof相关的一些问题
  3. Nginx —— ngx_http_core_module 模块提供的变量
  4. 机器学习实战读书笔记(1)
  5. Laravel 学习开篇
  6. Leetoce--572. 另一个树的子树(java)
  7. html是执行语言吗,HTML的基本语言
  8. 拿下微软、Google、Adobe,印度为何盛产科技圈 CEO?
  9. 《越狱》完结 米帅迷应小心纹身网站挂马
  10. Qt使用Qtxlsx读写xlsx文件
  11. 电脑计算机c盘缓存清理,电脑C盘缓存文件怎么删除
  12. SAP FB60\FB70\MIRO 默认税码配置
  13. Vivado 使用方法
  14. Linux系统版本大全
  15. oracle实验7 pl/sql编程基础
  16. 运用GoogleSketchUp创作城市雕塑
  17. 计算机专业职业取向,我的职业兴趣-我似乎对任何领域都有兴趣,有时会很想知道计算机及其网络是怎么设计运作的,...
  18. 国内外对于GaN中Fe相关点缺陷结构的局域特性的研究进展
  19. PyCharm的安装与使用
  20. 文献综述撰写格式及写作技巧

热门文章

  1. Jzoj4458 密钥破解——Pollard-rho
  2. Java:网络编程之UDP的使用
  3. websocket在.net4.5中实现的简单demo
  4. 【转】调试JavaScript 错误的解决方案
  5. 实现状态面板的显示与隐藏
  6. C# VC HTTP POST GET(转)
  7. NHibernate之旅(10):探索父子(一对多)关联查询
  8. Ubuntu 14.04安装mysql
  9. 开源数据库连接池之Tomcat内置连接池
  10. SectionIndexer中的getSectionForPosition()与getPositionForSection()