ToolsiOS学习iOS

SQLite数据库

2017-02-24  本文已影响423人  MiracleGl

SQLite是遵守ACID的关系数据库管理系统,它包含在一个相对小的C程序库中。与许多其它数据库管理系统不同,SQLite不是一个客户端/服务器结构的数据库引擎,而是被集成在用户程序中。-------维基百科


数据库简介

Navicat的使用

提示 : 数据库本身就是一个文件,可以用客户端来操作,实际开发是在Xcode中写SQL语句实现数据库的增删改查

Navicat演练SQL语句

以商品表为例 t_product。 创建 create 和删除 drop 数据库表

SQL语句之数据操作语句

以商品表为例 t_product。 数据操作语句包括 : 增 , 删 , 改;

Xcode原声SQLite演练

创建数据库和表

创建数据库文件的函数

/*
参数1 : 数据库的存储路径
参数2 : 数据库实例
返回值 : int
*/
sqlite3_open(<#const char *filename#>, <#sqlite3 **ppDb#>);


创建数据库表的函数

/*
参数1 : 数据库实例
参数2 : 要执行的SQL语句(建表)
参数3 : 建表成功的回调,传入NULL
参数4 : 回调的参数,传入NULL
参数5 : 错误信息
*/
sqlite3_exec(<#sqlite3 *#>, <#const char *sql#>, <#int (*callback)(void *, int, char **, char **)#>, <#void *#>, <#char **errmsg#>);

全局的数据库实例

{
    sqlite3 *_db;
}

创建数据库的函数sqlite3_open

/// 创建数据库
- (void)createDB
{
    /*
     创建并打开数据库
     这个函数会自动监测数据库是否已经存在,只有在数据库不存的时候才会去新建数据库并打开数据库

     参数1 : 数据库的路径
     参数2 : 数据库实例

     返回值 int
    */

    // 1.数据库路径
    NSString *SQLPath = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject] stringByAppendingPathComponent:@"SQL.db"];
    // 2.创建并打开数据库的函数
    int result = sqlite3_open(SQLPath.UTF8String, &_db);
    // 判断数据库是否创建打开成功
    if (result == SQLITE_OK) {
        NSLog(@"数据库创建打开成功");

        /*
         建表

         参数1 : 数据库实例
         参数2 : 建表的SQL语句
         参数3 : 函数执行成功的回调,不需要就写NULL
         参数4 : 回调的参数,没有就写NULL
         参数5 : 保存错误信息

         返回值 int
         */

        // 3.建表SQL语句
        NSString *createSQL = @"create table if not exists t_person(id integer primary key,name text not null,age integer);";
        // 保存错误信息
        char *errmsg = NULL;

        sqlite3_exec(_db, createSQL.UTF8String, NULL, NULL, &errmsg);
        if (errmsg == nil) {
            NSLog(@"建表成功");
        }
    }

    // 4.操作表
}


增删改
- (void)insert
{
    // 新增SQL语句
    NSString *insertSQL = @"insert into t_person(name,age) values('老王',21);";
    // 保存错误信息
    char *errmsg = NULL;

    sqlite3_exec(_db, insertSQL.UTF8String, NULL, NULL, &errmsg);
    if (errmsg == nil) {

        // 获取影响的行数
        int changes = sqlite3_changes(_db);
        NSLog(@"insert影响的行数 %d",changes);

        NSLog(@"新增成功");
    }
}

删除记录时,如果数据不存在,不会返回错误

- (void)delete
{
    // 删除SQL语句
    NSString *deleteSQL = @"delete from t_person where id = 4;";
    // 保存错误信息
    char *errmsg = NULL;

    sqlite3_exec(_db, deleteSQL.UTF8String, NULL, NULL, &errmsg);
    if (errmsg == nil) {

        // 获取影响的行数
        int changes = sqlite3_changes(_db);
        NSLog(@"delete影响的行数 %d",changes);

        NSLog(@"删除成功");
    }
}

更新记录时,如果指定的 id 不存在,不会返回错误

- (void)update
{
    // 修改SQL语句
    NSString *updateSQL = @"update t_person set name = '李雷' where id = 2;";
    // 保存错误信息
    char *errmsg = NULL;

    sqlite3_exec(_db, updateSQL.UTF8String, NULL, NULL, &errmsg);
    if (errmsg == nil) {

        // 获取影响的行数
        int changes = sqlite3_changes(_db);
        NSLog(@"update影响的行数 %d",changes);

        NSLog(@"修改成功");
    }
}

查询

- (void)query
{
    /*
     执行查询语句

     参数1 : 数据库实例
     参数2 : 查询语句
     参数3 : 查询语句的长度,传入-1,让函数自己算
     参数4 : 结果集,遍历结果集,取数据
     参数5 : 一般传入NULL

     返回值 int
     */

    // 查询SQL语句
    NSString *querySQL = @"select name,age from t_person;";
    // 结果集
    sqlite3_stmt *ppStmt = NULL;
    // 执行查询语句
    int result = sqlite3_prepare_v2(_db, querySQL.UTF8String, -1, &ppStmt, NULL);
    // 预编译 : 检查语法的有效性
    if (result == SQLITE_OK) {
        NSLog(@"查询数据失败");
    } else {
        NSLog(@"查询数据失败");
    }

    // 释放结果集 : 不然会内存泄露
    sqlite3_finalize(ppStmt);
}

- (void)query
{
    /*
     执行查询语句

     参数1 : 数据库实例
     参数2 : 查询语句
     参数3 : 查询语句的长度,传入-1,让函数自己算
     参数4 : 结果集,遍历结果集,取数据
     参数5 : 一般传入NULL

     返回值 int
     */

    // 查询SQL语句
    NSString *querySQL = @"select name,age from t_person;";
    // 结果集
    sqlite3_stmt *ppStmt = NULL;
    // 执行查询语句
    int result = sqlite3_prepare_v2(_db, querySQL.UTF8String, -1, &ppStmt, NULL);
    // 预编译 : 检查语法的有效性
    if (result == SQLITE_OK) {

        // 遍历结果集,逐条取数据,直到往下找,找不到数据为止
        while (sqlite3_step(ppStmt) == SQLITE_ROW) {

            /*
             参数1 : 结果集
             参数2 : 字段的索引,从主键后面开始计数
             */

            // 取name
            const unsigned char *cName = sqlite3_column_text(ppStmt, 0);
            NSString *ocName = [[NSString alloc] initWithCString:(const char *)cName encoding:NSUTF8StringEncoding];
            // 取age
            int age = sqlite3_column_int(ppStmt, 1);

            NSLog(@"%@ -- %d",ocName,age);
        }

    } else {
        NSLog(@"查询数据失败");
    }

    // 释放结果集 : 不然会内存泄露
    sqlite3_finalize(ppStmt);
}

FMDB

FMDB增删改查演练

数据库的创建和建表只需要执行一次

initialize : 这个类在第一次使用时就被调用一次,后面就不会再调用;而且是先于实例化方法调用的

+ (void)initialize
{
//    NSLog(@"这个类在第一次使用时就被调用一次");

    // 1.获取数据库路径
    NSString *SQLPath = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject] stringByAppendingPathComponent:@"heros.db"];

    // 2.创建数据库和建表,只会执行一次
    _db = [FMDatabase databaseWithPath:SQLPath];

    // 3.打开数据库
    BOOL isOpen = [_db open];
    if (isOpen) {
        // 4.建表
        BOOL isCreate = [_db executeUpdate:@"create table if not exists t_heros(id integer primary key,name text not null,age integer)"];
        if (isCreate) {
            NSLog(@"建表成功");
        }
    }
}


// 执行查询语句.获取到结果集
FMResultSet *resultSet = [_db executeQuery:@"select * from t_heros"];

// 遍历结果集,取数据
while ([resultSet next]) {

    // 取出来的数据
    NSString *name = [resultSet stringForColumn:@"name"];
    int age = [resultSet intForColumn:@"age"];
}

+ (NSArray *)selectHeros
{
    // 定义临时的模型数据
    NSMutableArray *tmpM = [NSMutableArray array];

    // 执行查询语句.获取到结果集
    FMResultSet *resultSet = [_db executeQuery:@"select * from t_heros"];

    // 遍历结果集,取数据
    while ([resultSet next]) {

        // 创建模型
        Heros *hero = [[Heros alloc] init];

        // 取出来的数据
        NSString *name = [resultSet stringForColumn:@"name"];
        int age = [resultSet intForColumn:@"age"];

        // 给模型赋值
        hero.name = name;
        hero.age = @(age);

        // 将模型添加到模型数组
        [tmpM addObject:hero];
    }

    return tmpM.copy;
}

感谢读到最后的朋友,最后祝大家工作顺利,请点赞支持一下,谢谢!

上一篇 下一篇

猜你喜欢

热点阅读