Android数据库高手(二)创建表和LitePal创建表

上一篇文章中我们学习了一些Android数据库基础知识,和几个颇为有用的SQLite命令,都是直接在命令行操作的。数据库是要和程序结合在一起,咱们来学习Android程序去操作SQLite数据库,还没看过前一篇文章的朋友可以先去参考 Android数据库高手(一)SQLite命令

操作数据库第一步创建表,传统创建表方法相信大多数人都知道,除了会展示传统的建表方法,还会讲解LitePal框架基本用法,并使用它来完成建表操作,让大家体会到使用框架操作数据库的魅力。

先来简单介绍一下,LitePal是一款开源Android数据库框架,采用对象关系映射(ORM)模式,平时开发最常用的数据库功能进行了封装,不用编写一行SQL语句就可以完成各种建表、増删改查的操作。并且LitePal很“轻”,jar包只有250k不到,而且近乎零配置,目前LitePal的源码已经托管到了GitHub上,地址是 https://github.com/LitePalFramework/LitePal

OK,简单介绍完了LitePal,我们还是先来看一下,在传统的Android开发中,需要怎么去创建表。

传统的建表方式

其实为了方便我们对数据库表进行管理,Android本身就提供了一个帮助类:SQLiteOpenHelper。这个类集创建和升级数据库于一身,并且自动管理了数据库版本,算是一个非常好用的工具。

那我们现在就来试试SQLiteOpenHelper的用法吧。首先你要知道SQLiteOpenHelper是一个抽象类,这意味着如果我们想要使用它的话,就需要创建一个自己的帮助类去继承它。SQLiteOpenHelper中有两个抽象方法,分别是onCreate()和onUpgrade(),我们必须在自己的帮助类里面重写这两个方法,然后分别在这两个方法中去实现创建、升级数据库的逻辑。本篇文章只需要把注意力放在创建数据库这里就行了,升级数据库我们会在下一篇文章中去讨论。

新建一个MySQLiteHelper类并让它继承SQLiteOpenHelper,这样一个最基本的数据库帮助类的代码如下所示:

public class MySQLiteHelper extends SQLiteOpenHelper {
 
    public MySQLiteHelper(Context context, String name, CursorFactory factory,
            int version) {
        super(context, name, factory, version);
    }
 
    @Override
    public void onCreate(SQLiteDatabase db) {
    }
 
    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    }
 
}

当数据库创建的时候会调用onCreate()方法,在这里去执行建表操作就可以了。比如说我们想新建一张news表,其中有title,content,publishdate,commentcount这几列,分别代表着新闻标题、新闻内容、发布时间和评论数,那么代码就可以这样写:

public class MySQLiteHelper extends SQLiteOpenHelper {
    
    public static final String CREATE_NEWS = "create table news ("
            + "id integer primary key autoincrement, "
            + "title text, "
            + "content text, "
            + "publishdate integer,"
            + "commentcount integer)";
 
    public MySQLiteHelper(Context context, String name, CursorFactory factory,
            int version) {
        super(context, name, factory, version);
    }
 
    @Override
    public void onCreate(SQLiteDatabase db) {
        db.execSQL(CREATE_NEWS);
    }
    ...
}

可以看到,我们把建表语句定义成了一个常量,然后在onCreate()方法中去执行了这条建表语句,news表也就创建成功了。这条建表语句虽然简单,但是里面还是包含了一些小的细节,我来解释一下。首先,根据数据库的范式要求,任何一张表都应该是有主键的,所以这里我们添加了一个自增长的id列,并把它设为主键。然后title列和content列都是字符串类型的,commentcount列是整型的,这都很好理解,但是publishdate列该怎么设计呢?由于SQLite中并不支持存储日期这种数据类型,因此我们需要将日期先转换成UTC时间(自1970年1月1号零点)的毫秒数,然后再存储到数据库中,因此publishdate列也应该是整型的。

现在,我们只需要获取到SQLiteDatabase的实例,数据库表就会自动创建了,如下所示:

SQLiteOpenHelper dbHelper = new MySQLiteHelper(this, "demo.db", null, 1);
SQLiteDatabase db = dbHelper.getWritableDatabase();

感觉很简单很方便是吗?那你就太容易满足了,下面我们就来学习一下LitePal的基本用法,看一看使用这个框架是如何实现同样的功能的。

LitePal的快速配置

首先我们需要将LitePal引入到项目当中,可以点击这里
在项目中的build.gradle添加依赖
dependencies {
implementation 'org.litepal.android:java:3.0.0'
}

  1. 配置litepal.xml
    接着在项目的assets目录下面新建一个litepal.xml文件,并将以下代码拷贝进去:
<?xml version="1.0" encoding="utf-8"?>
<litepal>
    <dbname value="demo" ></dbname>
 
    <version value="1" ></version>
 
    <list>
    </list>
</litepal>

配置文件相当简单,<dbname>用于设定数据库的名字,<version>用于设定数据库的版本号,<list>用于设定所有的映射模型,我们稍后就会用到。

  1. 配置LitePalApplication
    由于操作数据库时需要用到Context,而我们显然不希望在每个接口中都去传一遍这个参数,那样操作数据库就显得太繁琐了。因此,LitePal使用了一个方法来简化掉Context这个参数,只需要在AndroidManifest.xml中配置一下LitePalApplication,所有的数据库操作就都不用再传Context了,如下所示:
<manifest>
    <application
        android:name="org.litepal.LitePalApplication"
        ...
    >
    ...
    </application>
</manifest>

当然,有些程序可能会有自己的Application,并在这里配置过了。比如说有一个MyApplication,如下所示:

<manifest>
    <application
        android:name="com.example.MyApplication"
        ...
    >
    ...
    </application>
</manifest>

没有关系,这时只需要修改一下MyApplication的继承结构,让它不要直接继承Application类,而是继承LitePalApplication类,就可以使用一切都能正常工作了,代码如下所示:

public class MyApplication extends LitePalApplication {
    ...
}

但是,有些程序可能会遇到一些更加极端的情况,比如说MyApplication需要继承另外一个AnotherApplication,并且这个AnotherApplication还是在jar包当中的,不能修改它的代码。这种情况应该算是比较少见了,但是如果你遇到了的话也不用急,仍然是有解释方案的。你可以把LitePal的源码下载下来,然后把src目录下的所有代码直接拷贝到你项目的src目录下面,接着打开LitePalApplication类,将它的继承结构改成继承自AnotherApplication,再让MyApplication继承自LitePalApplication,这样所有的Application就都可以在一起正常工作了。

三步过后,配置工作弄完了,这是一件一本万利的事情,自此以后,使用LitePal提供的各种便利了,我们从建表开始。

开始建表

LitePal采取的是对象关系映射(ORM)的模式,这是个啥?JAVA是面向对象语言,SQLite数据库则是关系型数据库,面向对象和面向关系数据库之间建立一种映射关系,这就是对象关系映射。(一张表对应一个模型)

咱们为啥用对象关系映射模式?SQL语言理解起来费劲,写起来容易出错,面向对象咱们很擅长,我们使用面向对象的方式来操作数据库。对象关系映射很好地解决了这个问题,嗨了吧。

咱们瞧瞧LitePal中是如何建表。根据对象关系映射模式的理念,一张表对应一个模型(Model),建一张news表,有一个对应的News模型类。新建一个News类,如下所示:

package com.example.sqlitefeel;

public class News {
}

然后,表中每一列对应了模型类中的一个字段,比如news表中有id、title、content、publishdate、commentcount这几个列,那么在News类中就也应该有这几个字段,代码如下所示:

public class News {
    
    private int id;
    
    private String title;
    
    private String content;
    
    private Date publishDate;
    
    private int commentCount;
    
    // 自动生成get、set方法
    ...
}

其中id这个字段可写可不写,即使不写这个字段,LitePal在表中自动生成一个id列

LitePal所有映射自动完成。LitePa可以进行对象关系映射的数据类型一共有8种,int、short、long、float、double、boolean、String和Date。这8种数据类型的字段被自动映射到数据库表中,并不需要进行任何额外的配置。

现在模型类已经建好了,我们还差最后一步,就是将它配置到映射列表当中。编辑assets目录下的litepal.xml文件,在<list>标签中加入News模型类的声明:

<?xml version="1.0" encoding="utf-8"?>
<litepal>
    <dbname value="demo" />

    <version value="1" />

    <list>
        <mapping class="com.example.sqlitefeel.News"></mapping>
    </list>
</litepal>

注意这里一定要填入News类的完整类名。
现在对数据库有任何的操作,news表就会被自动创建出来。LitePal提供了一个便捷的方法来获取到SQLiteDatabase的实例,如下所示:

SQLiteDatabase db = Connector.getDatabase();

调用一下上述代码,news表已经创建成功了。我们使用在上一篇文章中学到的SQLite命令来查看一下,打开demo.db数据库,输入.table命令,结果如下图所示:

sqlite> .table
android_metadata  news              table_schema

可以看到,news表已经存在了。另外两张android_metadata和table_schema表是自动生成的,我们不用理。接下来我们还可以再查询一下news表的建表语句,如下图所示:

sqlite> select * from sqlite_master where name='news';
table|news|news|6|CREATE TABLE news (id integer primary key autoincrement,commentcount integer, content text, publishdate integer, title text)

看起来不够清新
sqlite> .mode line
sqlite> select * from sqlite_master where name='news';

    type = table
    name = news
tbl_name = news
rootpage = 6
     sql = CREATE TABLE news (id integer primary key autoincrement,
commentcount integer, content text, publishdate integer, title text)

这就是LitePal根据News类中的字段自动帮我们生成的建表语句,由此也说明,建表操作已经成功完成了。

我们也可同通过Android Studio 数据库插件看的更清晰


image.png

LitePal的用法有点入门了,那么本篇文章的内容就到这里,下篇文章当中我们将学习使用LitePal进行升级表的操作。感兴趣的朋友请继续阅读 Android数据库高手(三)——使用LitePal升级表

喜欢就点个赞把

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 218,386评论 6 506
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 93,142评论 3 394
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 164,704评论 0 353
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,702评论 1 294
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,716评论 6 392
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,573评论 1 305
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,314评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 39,230评论 0 276
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,680评论 1 314
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,873评论 3 336
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,991评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,706评论 5 346
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,329评论 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,910评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 33,038评论 1 270
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 48,158评论 3 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,941评论 2 355

推荐阅读更多精彩内容