FMDB是用于进行数据存储的第三方框架。它与SQLite与Core Data相比较,有很多优势
FMDB是面向对象的,它以OC的方式封装了SQLite得C语言API,使用起来更加方便,不需要过多的关心数据库操作的知识。
为什么不使用Core Data和SQLite?
Core Data是ORM(对象关系映射-Object Relational Mapping)的一种体现,实现了界面化操作,使用Core Data需要用到模型数据的转化,虽然操作简单,不需要直接操作数据库,但是性能能没有直接使用SQLite高,但是SQLite使用的时候需要使用C语言中的函数,操作麻烦,因此需要对它进行封装,但是只是简单的封装,很可能会忽略很多重要的细节,比如如何处理并发以及安全性更新问题。
新建SqliteManage类实现封装:
1 #import "SqleiteManage.h"
2 static SqleiteManage *manage = nil;
3 @implementation SqleiteManage
4
5 //单例保证是同一个数据库
6 +(instancetype)shareManage{
7 static dispatch_once_t onceToken;
8 dispatch_once(&onceToken, ^{
9 manage = [[SqleiteManage alloc]init];
10
11 });
12
13 return manage;
14 }
15
16 //打开数据库
17 -(int)openDB:(NSString *)str{
18 //1.打开数据库 建表
19 NSString *dbpath =[[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)lastObject]stringByAppendingPathComponent:str];
20 NSLog(@"%@",dbpath);
21
22 //打开数据库
23 result = sqlite3_open([dbpath UTF8String], &db);
24 if (SQLITE_OK ==result) {
25 NSLog(@"打开成功");
26 }else{
27 NSLog(@"打开失败");
28 }
29
30 return result;
31
32 }
33
34 //关闭数据库
35 -(int)closeDB{
36 return sqlite3_close(db);
37 }
38 //------建表
39 -(BOOL)creatTableWithSqlite:(NSString *)sql{
40
41 if (result ==SQLITE_OK) {
42
43 // 建表的SQL语句
44 // primary key autoincrement 定义 id为主键 值是自动增长的
45 // not null unique 不能为空 不能重复
46 // 建表的公式
47 // create table 表名 (字段名 字段的数据类型,字段名 字段的数据类型........);
48 // NSString *sql =@"create table if not exists user (id integer primary key autoincrement, name text not null unique, phone text, creatDate text);";
49 char *error;
50 int resul = sqlite3_exec(db, [sql UTF8String], NULL, NULL, &error);
51 [self closeDB];
52 if (resul == SQLITE_OK) {
53
54 NSLog(@"建表成功");
55 return YES;
56 // return 跳出整个函数
57 // black 是跳出括号
58
59 }else{
60 NSLog(@"%s",error);
61 return NO;
62 }
63
64 }
65 return NO;
66 }
67
68 //插入
69 -(BOOL)insertMessageWithSql:(NSString *)sql{
70 if (result == SQLITE_OK) {
71 char *error;
72 int resul = sqlite3_exec(db, [sql UTF8String], NULL, NULL, &error);
73 [self closeDB];
74 if (resul == SQLITE_OK) {
75 return YES;
76 }else{
77 return NO;
78 }
79
80 }
81
82 return NO;
83
84 }
85
86 //删除
87 -(BOOL)deleteMessageWithSql:(NSString *)sql{
88 if (result == SQLITE_OK) {
89 char *error;
90 int resul = sqlite3_exec(db, [sql UTF8String], NULL, NULL, &error);
91 [self closeDB];
92 if (resul == SQLITE_OK) {
93 return YES;
94 }else{
95 return NO;
96 }
97
98 }
99 return NO;
100 }
101
102 //修改
103 -(BOOL)modifyMessageWithSql:(NSString *)sql{
104 if (result == SQLITE_OK) {
105 char *error;
106 int resul = sqlite3_exec(db, [sql UTF8String], NULL, NULL, &error);
107 [self closeDB];
108 if (resul == SQLITE_OK) {
109 return YES;
110 }else{
111 return NO;
112 }
113
114 }
115
116 return NO;
117 }
118
119 -(NSArray*)queryMessageWithSQL:(NSString *)sql andObject:(NSString *)obj{
120 if (result==SQLITE_OK) {
121 // 声明一个结果集 查询的结果存放在结果集里面
122 sqlite3_stmt *stmt;
123 // 校验SQL语句是否正确 int nByte 为-1的时候 不限制 查询的长度
124 if (sqlite3_prepare_v2(db, [sql UTF8String], -1, &stmt, NULL)==SQLITE_OK) {
125 // like 模糊查询
126
127 NSString *searchContent =[NSString stringWithFormat:@"%%%@%%",obj];
128 // 绑定要查询的内容
129 if ( sqlite3_bind_text(stmt, 1, [searchContent UTF8String], -1, NULL)==SQLITE_OK
130 ) {
131 NSMutableArray * resultlist = [NSMutableArray array];
132 // 循环 查询
133 while ( sqlite3_step(stmt)== SQLITE_ROW) {
134 // 把查询到的一条数据 整合到一个字典里面
135
136 // 1 是 icol 查询到的这一条数据的列数
137 char *name =(char *) sqlite3_column_text(stmt, 1);
138 char *phone = (char *) sqlite3_column_text(stmt, 2);
139 char *time =(char *) sqlite3_column_text(stmt, 3);
140 NSDictionary *info =@{@"name":[NSString stringWithUTF8String:name],@"phone":[NSString stringWithUTF8String:phone],@"time":[NSString stringWithUTF8String:time],};
141 [resultlist addObject:info];
142 }
143 [self closeDB];
144 return resultlist;
145
146 }
147 }
148
149 }
150 //释放伴随指针
151 [stmt release];
152 return nil;
153 }
154 @end
封装后使用:
#import "ViewController.h"
#import "SqleiteManage.h"
@interface ViewController ()
//数据库(Database):按照数据结构来组织、存储和管理数据
//数据库基本是由表,关系,操作构成
//在移动平台开发常用的是SQLite
//以表(table)为单位
//表头的每一列 都是一个字段(clumn,属性)
//可以通过字段查找到对应的数据
//ios 使用C语言操作数据库
//***** 使用数据库之前的先添加;ibsqlite3框架#import<>
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
//************数据库相关概念***************
/*
ios使用数据库的重要方法
打开数据库:sqlite3_open()
建表 修改 添加 更新 删除数据:sqlite3_exec()
查询:1.效验语句是否合法:sqlite3_prepare_v2
2.绑定要查询的数据和sql语句:sqlite3_bind_text
3.循环查找内容(根据行):sqlite3_step
4.取出这一行里面的数据(根据对应的类型):sqlite3_column_text
关闭数据库:sqlite3_close()
SQL(Strured Query Language)是一种结构查询语言
SQL 语言特点:每一句后面都有一个;号结束 不区分大小写
SQL 的关键字:create update delete from where by table 。。。
在数据库里面不可以使用关键字来命名表名 或字段
数据库中的字符串 要用单引号 '' 括起来
sqlite 是关系型数据库
SQL语句使用公式
1.建表
@" create table (字段名 字段类型,字段名,字段类型);"
2.create table if not exists 表名(字段名,字段类型,)
如 :@"create table if not exists user(id integer,name text,phone text)
插入:insert into 表名(字段,字段)vlaus('内容','内容')
删除:delete from 表名 where 字段= '要删除的内容'
修改数据 :update 表名 set 字段 = '修改后的内容' where 字段 = '修改前的内容';
查询:
(1)select *from 表名 查询所有的字段(*表示所有);
(2)sele 字段1,字段2,......from 表名;
数据库的使用公式:
导入框架
1.创建数据库 打开数据库
2.创建表
3.添加 删除 修改 查询 内容 关闭数据库
//***********************************************************
*/
SqleiteManage * manage =[SqleiteManage shareManage];
// 打开数据库
[manage openDB:@"shujuku..sqlite"];
BOOL seccess = [manage creatTableWithSqlite: @"create table if not exists user (id integer primary key autoincrement, name text not null unique, phone text, creatDate text);"];
if (seccess) {
NSLog(@"建表成功");
}
// 插入数据公式
// insert into 表名 (字段,字段,字段) values ('','','');
NSString *name = @"小啊";
NSString * tel = @"13298822122";
NSString * date = @"2088-12-25";
// 插入数据
NSString *sql = [NSString stringWithFormat:@"insert into user (name, phone,creatDate) values ('%@','%@','%@');", name,tel,date ];
if ([manage insertMessageWithSql:sql]==YES) {
NSLog(@"插入数据成功");
}
// 删除数据
if ([manage deleteMessageWithSql:@"delete from user where name= '小明';"]==YES) {
NSLog(@"删除数据成功");
}
if ([manage modifyMessageWithSql:@"update user set name = '大黄人' where name = '白马王子';"]==YES) {
NSLog(@"修改数据成功");
}
// 查询数据
NSArray * list = [manage queryMessageWithSQL:@"select id,name,phone,creatDate from user where name like ?;" andObject:@"小"];
if (list.count !=0) {
NSLog(@"%@",list);
}
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
@end
封装后的Sqlite,减少了很多代码,所以使用FMDB会很方便。并且处理了多线程并发的问题,FMDB的封装也是这样的。