前言
移动端开发对于数据本地化的储存可有
文件储存
【即写入到本地文件中NSUserDefaults
的本质就是将数据按照key=value形式储存在plist
文件】,当然大量的数据字典储存还是得用强大的sqlite
。
一,SQLiteDB-集成
1.下载框架文件
- SQLiteDB官网 中下载文件解压拿到关键的.swift框架文件【
CloudDB.swift
,SQLTable.swift
,SQLiteBase.swift
,SQLiteDB.swift
】。
2.然后拖动到项目下
这里需要注意,swift文件应该来说全局可访问,不需要引入头文件,但是可能失效,所以我直接扔到项目下面没有成组。
3.Xcode添加db文件
在
Build Phases
下面添加.db
文件,这里的.db
文件可以是自己新建的或者公司的数据库.db文件【需要注意的是需要去SQLiteBase.swift里面修改DB_NAME
为导入的.db文件名】,当然太懒了在官方下载包里面添加data.db也可以。至于如何操作自己的库后面也会写。
4.新建侨接文件
在项目名称右键新建文件->选择
Cocoa Touch Class
文件点击Next
输入侨接类的名称随便起名即可我这里【
brid_head
】,Subclass of选择UIView
,Language选择Objective-C
点击Next。
如下选择swiftUIStudy点击Create
有些Xcode可能会自动提示生成侨接文件。可以点击ok自动生成
项目名_Bridging-Header.h
最后删除brid_head.h以及brid_head.m文件,但是像我的Xcode有时候能自动生成侨接文件,有时候不会生成桥接文件,这时候我们只需要将下面语句复制到brid_head.h
文件或项目名_Bridging-Header.h
里面。
#import "sqlite3.h"
#import <time.h>
然后我们去点击项目如下图中1--->
Build Setting
----->图中2 combined
----->Swift Compiler - General
双击Objective-C Bridging Header 后面空白出拖动或者粘贴brid_head.h的路径即可。
二,SQLiteDB-操作
1.新建UI页面
新建操作数据库的专有页面
2.SQLiteDB源码阅读
///1.shared源码这里初始化创建SQLiteDB实例static修饰作为单利提供给外界访问。
/// Singleton instance for access to the SQLiteDB class
static let shared = SQLiteDB()
//2.dbPath作为本地数据库路径。根据代码我们可以看出如果dbPath为null那么默认会获取项目下的DB_NAME=data.db
//作为空数据库容器,inMemory是使用内存数据库还是磁盘数据库。我们以db文件的形式就是默认false即磁盘数据库
override func open(dbPath: String = "", copyFile: Bool = true, inMemory: Bool = false) -> Bool {
NSLog("DB Open called with path: \(dbPath)")
var path = ""
if !inMemory {
if dbPath.isEmpty {
guard let url = Bundle.main.resourceURL else { return false }
path = url.appendingPathComponent(DB_NAME).path
} else {
path = URL(fileURLWithPath: dbPath).path
}
}
NSLog("Calling Super Open with path: \(path)")
return super.open(dbPath: path, copyFile: copyFile, inMemory: inMemory)
}
.
.
.
.
封装了很多方法可以自己看哦
3.SQLiteDB初步使用
通过
SQLiteDB.shared
实例化SQLiteDB,.open()
打开数据库,通过.execute(sql:"数据库操作语句")
进行操作即可。如下代码:
import SwiftUI
struct Swift_Sqlite_UIView: View {
//1.获取数据库实例
var db:SQLiteDB=SQLiteDB.shared
var body: some View {
VStack(){
Text("SQLiteDB操作").modifier(TitleStyle())
//1.数据库操作打开DB链接
HStack{
Text("open").onTapGesture {
//2.这里进行打开数据库
_=self.db.open()
//3.执行创建表操作操作
_=self.db.execute(sql: "create table if not exists users(uid integer primary key,uname varchar(20),description varchar(20))")
print("path=\(homePath())")
}.modifier(Title())
}.modifier(StackStyle(alignment:Alignment.topLeading))
}.modifier(StackStyle(alignment:Alignment.top))
}
}
struct Swift_Sqlite_UIView_Previews: PreviewProvider {
static var previews: some View {
Swift_Sqlite_UIView()
}
}
//modifier
struct TitleStyle: ViewModifier {
func body(content: Content) -> some View {
content.padding(EdgeInsets(top: 66,leading: 1,bottom: 1,trailing: 1)).font(/*@START_MENU_TOKEN@*/.title/*@END_MENU_TOKEN@*/)
}
}
struct Title: ViewModifier {
func body(content: Content) -> some View {
content.padding(EdgeInsets(top: 16,leading: 11,bottom: 1,trailing: 1)).font(.title)
}
}
struct StackStyle: ViewModifier{
var alignment=Alignment.top
var screenBounds:CGRect = UIScreen.main.bounds
func body(content: Content) -> some View {
content.frame(width:screenBounds.width, height: screenBounds.height, alignment:alignment)
}
}
- 运行之前记得更改运行启动界面如下再运行:
接着点击open,我们看到返回结果是1。说明创建成功。
4.建表是否成功[验证]
代码中我们打印了模拟器的路径,我们需要点进去看看当前是否创建表成功。我们那事实说话。一下代码我们能打印模拟器路径:
func homePath() -> NSString {
return NSHomeDirectory() as NSString;
}
打开终端输入open 路径如下:
-
点击回车,出现一堆文件夹有一个高亮的文件夹图中1,点击Documents->出现data.db
-
点击Documents或者Library->出现data.db 我们利用Navicat Premium 等工具打开数据库查看表
-
查看data.db表如下
验证成功
:
5.SQLiteDB-增查改删
---存粹的sql语句拼接
SQLiteDB之所以好用其原因就是直白的使用sql语句即可。
【1】增
:
Text("insert").onTapGesture {
let uname = "王飞"
let description = "路很长"
//插入数据库,这里用到了esc字符编码函数,其实是调用bridge.m实现的
let sql = "insert into persons(uname,description) values('\(uname)','\(description)')"
print("sql: \(sql)")
//通过封装的方法执行sql
let result = db.execute(sql: sql)
print(result)
}.modifier(Title())
- 运行看效果同样方式拿到路径终端打开,数据表查看
插入成功!
【2】查
:
//查询数据
Text("select").onTapGesture {
let uname = "王飞"
//插入数据库,这里用到了esc字符编码函数,其实是调用bridge.m实现的
let sql = "select uname from persons where uname='\(uname)'"
print("sql: \(sql)")
//通过封装的方法执行sql
let result = db.query(sql: sql)
//获取最后一行数据显示
let name = result[0]["uname"] as? String
print("数据库数据来了=\(String(describing: name))")
}.modifier(Title())
打印结果ok
【3】改
:
//跟新数据
Text("updata").onTapGesture {
let uname = "大飞飞"
//插入数据库,这里用到了esc字符编码函数,其实是调用bridge.m实现的
let sql = "update persons set uname = '\(uname)'"
print("sql: \(sql)")
//通过封装的方法执行sql
_ = db.execute(sql: sql)
//查询
let selectSql = "select uname from persons"
print("sql: \(selectSql)")
//通过封装的方法执行sql
let results = db.query(sql: selectSql)
let name = results[0]["uname"] as? String
print("修改之后的数据=\(String(describing: name))")
}.modifier(Title())
【4】删
:
记住每次运行需要重新打开,插入,然后删除。不然报错
超出索引异常
。
//删除数据
HStack{
Text("delete").onTapGesture {
let uname = "大飞飞"
//删除满足条件数据
let sql = "delete from persons where uname = '\(uname)'"
print("sql: \(sql)")
//通过封装的方法执行sql
_ = db.execute(sql: sql)
//查询
let selectSql = "select *from persons"
print("sql: \(selectSql)")
//通过封装的方法执行sql
let results = db.query(sql: selectSql)
let name = results.count
print("修改之后的数据个数=\(String(name))个")
}.modifier(Title())
}.modifier(StackStyle(alignment:Alignment.topLeading,height: 66))
三,SQLiteDB-操作任意.db文件
,在SQLiteDB.swift进行修改DB_NAME="bhnes.db"
操作如下,新增bhnes.db,
-
表结构如下:
-
代码如下
VStack{
Text("操作其他.db文件").onTapGesture {
db.open()
let uname = "大飞飞"
//删除满足条件数据
let sql = "delete from persons where uname = '\(uname)'"
print("sql: \(sql)")
//通过封装的方法执行sql
_ = db.execute(sql: sql)
//查询
let selectSql = "select *from persons"
print("sql: \(selectSql)")
//通过封装的方法执行sql
let results = db.query(sql: selectSql)
let name = results.count
print("修改之后的数据个数=\(String(name))个")
}.offset(x:80.0, y:10).modifier(TitleStyle()).foregroundColor(.red)
Text("查询").onTapGesture {
_=self.db.open()
//插入数据库,这里用到了esc字符编码函数,其实是调用bridge.m实现的
let sql = "select name from EquipType where code='Z'"
print("sql: \(sql)")
//通过封装的方法执行sql
let result = db.query(sql: sql)
//获取最后一行数据显示
let name = result[0]["name"] as? String
print("数据库数据来了=\(String(describing: name))")
DispatchQueue.main.async {
if (!(name!.isEmpty)){
self.queryResult = name! as String
self.flag=true
}
}
}.modifier(Title()).offset(x: -60.0, y: 10.0)
Text(self.flag ? queryResult : "查询结果").modifier(Title())
}.modifier(StackStyle(alignment:Alignment.topLeading,height: 266))
- 点击查询按钮:跟新控件如下
接下来我们进行操作自己数据库。
....下午继续