创建数据库过程需要3个步骤:
1、使用sqlite3_open函数打开数据库;
2、使用sqlite3_exec函数执行create table语句,创建数据库表;
3、使用sqlite3_close函数释放资源。
这个过程中使用了3个sqlite3函数,它们都是纯c语言函数,通过objective-c去调用c函数当然不是什么问题,但是也要注意objective-c数据类型与c数据类型兼容性问题。
下面我们使用sqlite技术实现备忘录案例,与属性列表文件实现一样,我们只需要修改持久层工程(persistencelayer)中notedao类就可以了。首先我们需要添加sqlite3库到工程环境中,有3个工程需要添加到哪个呢?应该添加到可以运行的工程即表示层工程presentationlayer。选择工程presentationlayer中targets→presentationlayer→link binary with libraries,点击左下角的“+”,弹出对话框选择libsqlite3.dylib或libsqlite3.0.dylib,在弹出的对话框中点击add添加。

notedao.h文件的修改:
我们需要使用语句#import ”sqlite3.h”引入sqlite3头文件,而且需要定义sqlite3*成员变量db。notedao.m中的createeditablecopyofdatabaseifneeded方法:
createeditablecopyofdatabaseifneeded方法用于创建数据库,第1步打开数据库,代码①行,语句是sqlite3_open([writabledbpath utf8string], &db),sqlite3_open函数的第1个参数是数据库文件完整的路径,但是需要注意的是在sqlite3函数中接受的是char*的utf-8类型数据,需要将nsstring*转换为utf-8,使用nsstring*的utf8string方法可以转换,sqlite3_open函数第2个参数sqlite3指针变量db的地址。该函数的返回值是int类型,在sqlite3中定义了很多常量,返回值等于常量sqlite_ok则说明操作成功。
第2步执行建表语句,代码第④行,语句sqlite3_exec(db,[createsql utf8string],null,null,&err)执行建表的sql。第1个参数是sqlite3指针变量db的地址,第2个参数是要执行的sql语句,第3个参数是要回调函数,第4个参数是要回调函数的参数,第5个参数是执行出错的字符串。建表sql语句是,如果表note存在这不用创建。
create table if not exists note (cdate text primary key, content text)
第3步使用sqlite3_close函数释放资源,代码②、⑤、⑦行所示,在数据库打开失败、create table执行失败和成功执行完成时候调用。原则上无论正常结束还是异常结束必须使用sqlite3_close函数释放资源。
数据查询一般会带有查询条件,这个使用sql语句where子句很容易实现,但是在程序中需要动态绑定参数给where子句。执行查询数据步骤如下:
2、使用sqlite3_prepare_v2函数预处理sql语句;
3、使用sqlite3_bind_text函数绑定参数;
4、使用sqlite3_step函数执行sql语句,遍历结果集;
5、使用sqlite3_column_text等函数提取字段数据;
6、使用sqlite3_finalize和sqlite3_close函数释放资源。
notedao.m中的按照主键查询数据方法:
该方法执行了6个步骤,其中第1个步骤,代码第①行所示,它与创建数库的第1个步骤是一样的,不用再介绍了。
第2个步骤,代码第③行所示,语句sqlite3_prepare_v2(db, [qsql utf8string], -1, &statement, null)是预处理sql语句,预处理目的是将sql编译成二进制代码,提高sql语句执行的速度。sqlite3_prepare_v2函数的第3个参数-1代表全部sql字符串长度,第4个参数&statement是sqlite3_stmt指针的地址,它是语句对象,通过语句对象可以执行sql语句,第5个参数是sql语句没有被执行的部分语句。
第3个步骤,代码第⑤行所示,语句sqlite3_bind_text(statement, 1, [nsdate utf8string], -1, null)是绑定sql语句参数。在sql语句中带有问号,这个问号就是要绑定的参数,问号是占位符。
nsstring *qsql = @”select cdate,content from note where cdate =?”;
sqlite3_bind_text函数是绑定参数,第1个参数是statement指针,第2个参数为序号(从1开始),第3个参数为字符串值,第4个参数为字符串长度,第5个参数为一个函数指针。
第4个步骤sqlite3_step(statement)执行sql语句,代码第⑥行所示,sqlite3_step返回int类型,等于sqlite_row说明还要其它的行没有遍历。
第5个步骤提取字段数据,代码第⑦行所示,使用sqlite3_column_text(statement, 0)函数可以读取字符串类型字段,第2参数是指定select字段的索引(从0开始)。同样char*转换成为nsstring*类型,需要initwithutf8string:构造方法。读取字段函数采用与字段类型有关系,sqlite3的类似的常用函数还有:
sqlite3_column_blob()
sqlite3_column_double()
sqlite3_column_int()
sqlite3_column_int64()
sqlite3_column_text()
sqlite3_column_text16()
关于其它的api可以参考http://www.sqlite.org/cintro.html。
第6个步骤是释放资源,创建数据库过程不同,除了使用sqlite3_close函数关闭数据库,代码第⑧行所示,还要使用sqlite3_finalize函数释放语句对象statement代码第⑨行所示。
notedao.m中的查询所有数据方法:
查询所有数据方法与按照主键查询数据方法类似,区别在于本方法没有查询条件不需要绑定参数。遍历的时候使用while循环语句,不是if语句。
while (sqlite3_step(statement) == sqlite_row) {
… …
}
修改数据包括:insert、update和delete语句。这3个sql语句都可以带有参数,关于参数的绑定与查询where子句绑定的方式是一样的。执行修改数据步骤如下:
4、使用sqlite3_step函数执行sql语句;
5、使用sqlite3_finalize和sqlite3_close函数释放资源。
修改数据的步骤与查询数据的步骤相比少了一个提取字段数据步骤。下面我们看看代码部分。其它的步骤是一样的。
notedao.m中的插入note方法:
第⑤行代码sqlite3_step(statement)语句执行插入语句,常量sqlite_done执行完成。
notedao.m中的删除note方法: