import UIKit

class SQLiteManager: NSObject {

    private static let manager: SQLiteManager = SQLiteManager()
/// 单粒
class func shareManager() ->SQLiteManager {
return manager
} // 数据库对象
private var db:COpaquePointer = nil // 创建一个串行队列
private let dbQueue = dispatch_queue_create("com.520it.lnj", DISPATCH_QUEUE_SERIAL) func execQueueSQL(action: (manager: SQLiteManager)->())
{
// 1.开启一个子线程
dispatch_async(dbQueue) { () -> Void in
print(NSThread.currentThread())
// 2.执行闭包
action(manager: self)
}
} /**
打开数据库 :param: SQLiteName 数据库名称
*/
func openDB(SQLiteName: String)
{
// 0.拿到数据库的路径
let path = SQLiteName.docDir()
print(path)
let cPath = path.cStringUsingEncoding(NSUTF8StringEncoding)!
// 1.打开数据库
/*
1.需要打开的数据库文件的路径, C语言字符串
2.打开之后的数据库对象 (指针), 以后所有的数据库操作, 都必须要拿到这个指针才能进行相关操作
*/
// open方法特点: 如果指定路径对应的数据库文件已经存在, 就会直接打开
// 如果指定路径对应的数据库文件不存在, 就会创建一个新的
if sqlite3_open(cPath, &db) != SQLITE_OK
{
print("打开数据库失败")
return
} // 2.创建表
if creatTable()
{
print("创建表成功")
}else
{
print("创建表失败")
}
} private func creatTable() -> Bool
{
// 1.编写SQL语句
// 建议: 在开发中编写SQL语句, 如果语句过长, 不要写在一行
// 开发技巧: 在做数据库开发时, 如果遇到错误, 可以先将SQL打印出来, 拷贝到PC工具中验证之后再进行调试
let sql = "CREATE TABLE IF NOT EXISTS T_Person( \n" +
"id INTEGER PRIMARY KEY AUTOINCREMENT, \n" +
"name TEXT, \n" +
"age INTEGER \n" +
"); \n"
// print(sql)
// 2.执行SQL语句
return execSQL(sql)
} /**
执行除查询以外的SQL语句 :param: sql 需要执行的SQL语句 :returns: 是否执行成功 true执行成功 false执行失败
*/
func execSQL(sql: String) -> Bool
{
// 0.将Swift字符串转换为C语言字符串
let cSQL = sql.cStringUsingEncoding(NSUTF8StringEncoding)! // 在SQLite3中, 除了查询意外(创建/删除/新增/更新)都使用同一个函数
/*
1. 已经打开的数据库对象
2. 需要执行的SQL语句, C语言字符串
3. 执行SQL语句之后的回调, 一般传nil
4. 是第三个参数的第一个参数, 一般传nil
5. 错误信息, 一般传nil
*/
if sqlite3_exec(db, cSQL, nil, nil, nil) != SQLITE_OK
{
return false
}
return true
} /**
查询所有的数据
:returns: 查询到的字典数组
*/
func execRecordSQL(sql: String) ->[[String: AnyObject]]
{
// 0.将Swift字符串转换为C语言字符串
let cSQL = sql.cStringUsingEncoding(NSUTF8StringEncoding)! // 1.准备数据
// 准备: 理解为预编译SQL语句, 检测里面是否有错误等等, 它可以提供性能
/*
1.已经开打的数据库对象
2.需要执行的SQL语句
3.需要执行的SQL语句的长度, 传入-1系统自动计算
4.预编译之后的句柄, 已经要想取出数据, 就需要这个句柄
5. 一般传nil
*/
var stmt: COpaquePointer = nil
if sqlite3_prepare_v2(db, cSQL, -, &stmt, nil) != SQLITE_OK
{
print("准备失败")
} // 准备成功
var records = [[String: AnyObject]]() // 2.查询数据
// sqlite3_step代表取出一条数据, 如果取到了数据就会返回SQLITE_ROW
while sqlite3_step(stmt) == SQLITE_ROW
{
// 获取一条记录的数据
let record = recordWithStmt(stmt)
// 将当前获取到的这一条记录添加到数组中
records.append(record)
} // 返回查询到的数据
return records
} /**
获取一条记录的值 :param: stmt 预编译好的SQL语句 :returns: 字典
*/
private func recordWithStmt(stmt: COpaquePointer) ->[String: AnyObject]
{
// 2.1拿到当前这条数据所有的列
let count = sqlite3_column_count(stmt)
// print(count)
// 定义字典存储查询到的数据
var record = [String: AnyObject]() for index in ..<count
{
// 2.2拿到每一列的名称
let cName = sqlite3_column_name(stmt, index)
let name = String(CString: cName, encoding: NSUTF8StringEncoding)!
// print(name)
// 2.3拿到每一列的类型 SQLITE_INTEGER
let type = sqlite3_column_type(stmt, index)
// print("name = \(name) , type = \(type)") switch type
{
case SQLITE_INTEGER:
// 整形
let num = sqlite3_column_int64(stmt, index)
record[name] = Int(num)
case SQLITE_FLOAT:
// 浮点型
let double = sqlite3_column_double(stmt, index)
record[name] = Double(double)
case SQLITE3_TEXT:
// 文本类型
let cText = UnsafePointer<Int8>(sqlite3_column_text(stmt, index))
let text = NSString(CString: cText, encoding: NSUTF8StringEncoding)!
record[name] = text
case SQLITE_NULL:
// 空类型
record[name] = NSNull()
default:
// 二进制类型 SQLITE_BLOB
// 一般情况下, 不会往数据库中存储二进制数据
print("")
}
}
return record
} }

使用事务插入数据:

       let manager = SQLiteManager.shareManager()

        // 开启事务
manager.beginTransaction() for i in ..<
{
let p = Person(dict: ["name": "zs + \(i)", "age": + i])
p.insertPerson() if i ==
{
manager.rollbackTransaction()
// 注意点: 回滚之后一定要跳出循环停止更新
break
}
} // 提交事务
manager.commitTransaction()

预编译绑定:

    //1、打开数据库
sqlite3 *db = [self sqlite3_open_database];
//2、建立预编译语句对象并编译
charchar *sql = "INSERT INTO student(name,age) VALUES(?,?)";//?为占位符,代表此处将来用变量值替换
//2.1、准备预编译语句对象
sqlite3_stmt *stmt = NULL;
//2.2、预编译sql语句
int result = sqlite3_prepare_v2(db, sql, -, &stmt, NULL);
//2.3、预编译成功,绑定值
if (result == SQLITE_OK) {
//绑定界面数据到预编译sql语句中
sqlite3_bind_text(stmt, , [self.txtName.text UTF8String], -, NULL);
sqlite3_bind_int(stmt, , [self.txtAge.text intValue]);
//3、执行预编译语句对象,4、使用结果
result = sqlite3_step(stmt);
if (result == SQLITE_DONE) {
[self myAlert:@"插入数据成功!"];
} else {
[self myAlert:@"插入数据失败!"];
}
}
//5、销毁预编译语句对象,关闭数据库
sqlite3_finalize(stmt);
sqlite3_close(db);

第十二篇、Swift_Sqlite的使用的更多相关文章

  1. 解剖SQLSERVER 第十二篇 OrcaMDF 行压缩支持(译)

    解剖SQLSERVER 第十二篇   OrcaMDF 行压缩支持(译) http://improve.dk/orcamdf-row-compression-support/ 在这两个月的断断续续的开发 ...

  2. 第十二篇 SQL Server代理多服务器管理

    本篇文章是SQL Server代理系列的第十二篇,详细内容请参考原文 在这一系列的上一篇,我们查看了维护计划,一个维护计划可能会创建多个作业,多个计划.你还简单地看了SSIS子系统,并查看了维护计划作 ...

  3. 第十二篇 Integration Services:高级日志记录

    本篇文章是Integration Services系列的第十二篇,详细内容请参考原文. 简介在前一篇文章我们配置了SSIS内置日志记录,演示了简单和高级日志配置,保存并查看日志配置,生成自定义日志消息 ...

  4. Python之路【第十二篇】:JavaScrpt -暂无内容-待更新

    Python之路[第十二篇]:JavaScrpt -暂无内容-待更新

  5. Python开发【第二十二篇】:Web框架之Django【进阶】

    Python开发[第二十二篇]:Web框架之Django[进阶]   猛击这里:http://www.cnblogs.com/wupeiqi/articles/5246483.html 博客园 首页 ...

  6. 【译】第十二篇 Integration Services:高级日志记录

    本篇文章是Integration Services系列的第十二篇,详细内容请参考原文. 简介在前一篇文章我们配置了SSIS内置日志记录,演示了简单和高级日志配置,保存并查看日志配置,生成自定义日志消息 ...

  7. 【译】第十二篇 SQL Server代理多服务器管理

    本篇文章是SQL Server代理系列的第十二篇,详细内容请参考原文 在这一系列的上一篇,我们查看了维护计划,一个维护计划可能会创建多个作业,多个计划.你还简单地看了SSIS子系统,并查看了维护计划作 ...

  8. 跟我学SpringCloud | 第十二篇:Spring Cloud Gateway初探

    SpringCloud系列教程 | 第十二篇:Spring Cloud Gateway初探 Springboot: 2.1.6.RELEASE SpringCloud: Greenwich.SR1 如 ...

  9. Egret入门学习日记 --- 第十二篇(书中 5.1节 内容)

    第十二篇(书中 5.1节 内容) 昨天把 第4章完成了. 今天来看第5章. 接下来是 5.1节 的内容. 总结一下 5.1节 的重点: 1.如何制作一个公用按钮皮肤. 跟着做: 重点1:如何制作一个公 ...

  10. Spring Cloud第十二篇 | 消息总线Bus

    ​ ​本文是Spring Cloud专栏的第十二篇文章,了解前十一篇文章内容有助于更好的理解本文: Spring Cloud第一篇 | Spring Cloud前言及其常用组件介绍概览 Spring ...

随机推荐

  1. epoll使用具体解释(精髓)

    epoll - I/O event notification facility 在linux的网络编程中,非常长的时间都在使用select来做事件触发.在linux新的内核中,有了一种替换它的机制,就 ...

  2. [AngularJS] Test an Angular Component with $componentController

    Traditionally you had to create DOM elements to test a directive but by shifting our focus to compon ...

  3. ios开发——常用经典算法OC篇&冒泡/快速

    冒泡排序与快速排序 1.序言 ios开发中涉及到算法的地方还真不多,除非你的应用程序真的非常大,或者你想你的应用程序性能非常好才会去想到关于算法方面的性能优化,而在ios开发中真的能用得到的也就是关于 ...

  4. ConfigurationManager.GetSection()方法的使用

    GetSection方法读取的是configSections节点,这个节点在web.config配置文件中,它比较特殊,必须放置于首节点,也就是说,在它之前不能有其它类型的节点.configSecti ...

  5. Flex4之元数据标签使用

    Flex 元数据标签 1.[ArrayElementType] 使用ArrayElementType元数据标签可以让你定义数组元素的数据类型. 程序代码: [ArrayElementType(&quo ...

  6. Python dictionary implementation

    Python dictionary implementation http://www.laurentluce.com/posts/python-dictionary-implementation/ ...

  7. C++编译器默默编写并调用哪些函数

    什么时候empty class(空类)不再是个empty class呢?当C++处理过它之后,是的,如果你自己没有声明,编译器就会为它声明(编译器版本)一个copy构造函数.一个copy assign ...

  8. 从cin读入一组词并把它们存入一个vector对象,然后设法把所有词都改写为大写字母。

    #include<iostream> #include<vector> #include<string> using namespace std; int main ...

  9. PHP设计模式之策略模式

    前提: 在软件开发中也常常遇到类似的情况,实现某一个功能有多种算法或者策略,我们可以根据环境或者条件的不同选择不同的算法或者策略来完成该功能.如查 找.排序等,一种常用的方法是硬编码(Hard Cod ...

  10. 替换运算符 shell

        ${变量:-word}如果变量存在且非空,则返回其值:否则返回word                  用于:如果变量未定义,则返回默认值即word      ${变量:+word}如果变量 ...