数据持久化的本质就是把数据由内写到本地(硬盘中),在iOS指将数据写到沙盒文件夹下;
沙盒机制:指的就是采用沙盒文件夹的形式管理应用程序的本地文件,而且沙盒文件夹的名字是随机分配的,采用十六进制方法命名;
=======================关于沙盒目录==========================
沙盒内部构造:
测试沙盒:
属性:
@interface ViewController () @property (retain, nonatomic) IBOutlet UITextField *nameField; @property (retain, nonatomic) IBOutlet UITextField *passwordField; @property(nonatomic,retain)NSUserDefaults *user; @end
//登录按钮
- (IBAction)handleLgin:(UIButton *)sender { //取出输入框中的数据 NSString *name = self.nameField.text; NSString *password = self.passwordField.text; //取出用户偏好设置 NSString *pName = [self.user valueForKey:@"name"]; NSString *pPassword = [self.user valueForKey:@"password"]; //当输入的内容和本地存储的信息相同时显示登录成功 if ([name isEqualToString:pName] && [password isEqualToString:pPassword]) { NSLog(@"登陆成功"); }else{ NSLog(@"登录失败,请注册"); } }
//注册按钮
- (IBAction)handleRegister:(UIButton *)sender { NSString *name = self.nameField.text; NSString *password = self.passwordField.text; //当不输入内容的时候提前结束方法 if (name.length == 0 || password.length == 0) { NSLog(@"账户名或者密码为空,注册失败!"); return; } //本地文件中设置用户名和用户密码 //设置用户名 [self.user setObject:name forKey:@"name"]; //设置用户密码 [self.user setObject:password forKey:@"password"]; //同步数据 [self.user synchronize]; NSLog(@"注册成功"); }
记得释放:
- (void)dealloc { [_nameField release]; [_passwordField release]; self.user = nil; [super dealloc]; }
测试结果:
————————————————————————
————————————————————————————
1.获取沙盒文件夹的路径
NSHomeDirectory() 沙盒文件的主目录,在这个文件夹下放着三个文件Document,Libralay,Tmp,其中Library 中还有两个文件Caches,Perference,系统帮我们创建五个文件存放在沙盒文件下,这五个是不能删除的
NSLog(@"%@",NSHomeDirectory());
Documents: 存放一些比较重要的文件,文件大小比较小,这些都是可以有副本,此文件夹中不能有太多东西,否则在上传AppStore中会直接被拒,比如: 数据库
获取Documents 文件夹的路径
第一个参数:文件夹的名字 64行
第二个参数:搜索域,有优先级:users -->local -->network -->system
第三个参数:相对路径或者是绝对路径 YES绝对路径,NO代表相对路径
此方法最早是应用在MAC端开发的,对于PC 端可以有很多的用户,所以该方法的返回值是一个数组,但是现在这个方法应用在移动端(iOS端),而移动端用户只有一个,所以获取的路径也只有一个
NSString *documentsPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)lastObject]; NSLog(@"%@",documentsPath);
Library 资源库,存放的一些不太重要的文件,相对比较大,且其中有两个子文件
NSString *libraryPath = [NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES)lastObject]; NSLog(@"%@",libraryPath);
Caches 存放一些缓存的文件,如网页缓存,图片缓存,视频缓存,视频缓存,应用中"清除缓存"功能,清理的就是这个文件夹里面的内容
//获取Caches路径
NSString *cachesPath = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES)lastObject]; NSLog(@"%@",cachesPath);
//Perferences 偏好设置,存放一些用户的信息
注意:路径是找不到的,只能通过NSUserDefaults 访问
NSUserDefaults *user = [NSUserDefaults standardUserDefaults];
//perferences 中存放的都是plist 文件,在第一次设置键值对的时候,会帮你创建plist文件,如果直接取值的时候,plist 文件是没有的
赋值和取值:
// [user setBool:YES forKey:@"login"]; //取出BOOL值 //BOOL isLogin = [user boolForKey:@"login"]; // NSLog(@"%d",isLogin);
//NSUserDefaults 支持的数据类型:array,dictionary,string,data,number,bool,integer等
//NSUserDefaults 中一般存储数值类型的数据,不存放大型的数据
//模拟启动用户引导图
BOOL isFirstLogin = [user boolForKey:@"login"]; if (NO == isFirstLogin) { NSLog(@"第一次启动"); [user setBool:YES forKey:@"login"]; [user synchronize];//立即同步 }else{ NSLog(@"不是第一次启动"); }
//Tem 存放临时文件 比如:压缩包 zip ,解压后就删除处理了
获取Tem的路径
NSTemporaryDirectory(); NSLog(@"%@",NSTemporaryDirectory()
NSFileManager 文件管理类,是一个文件管理工具,主要用于文件的的添加、删除、拷贝,继承自 NSObject
NSFileManager 也是一个单例类
NSFileManager *fileManger = [NSFileManager defaultManager];
=======================文件的创建==========================
NSFileManager常用操作一览表:
//在Document 文件下创建一个文件 av.text
1.获取Documents 路径
NSString *documentsPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)lastObject];
2.创建av.text 的路径
// stringByAppendingFormat 拼接上什么就得到什么 // stringByAppendingString 拼接上什么就得到什么 // stringByAppendingPathExtension 拼接的内容前加一个点 // stringByAppendingPathComponent 拼接的内容前加一个 /
NSString *avPath = [documentsPath stringByAppendingPathComponent:@"av"]; NSLog(@"%@",avPath);
首先判断文件是否存在
<span style="color:#3333ff;"> if ([fileManger fileExistsAtPath:avPath]) { NSLog(@"存在"); }else{ NSLog(@"不存在"); </span><span style="color:#cc0000;"> //创建 av.text文件 //第二个参数询问:如果路径中没有文件夹是否自动创建</span><span style="color:#3333ff;"> BOOL isSuccss = [fileManger createDirectoryAtPath:avPath withIntermediateDirectories:YES attributes:nil error:nil]; if (isSuccss) { NSLog(@"创建成功"); }else{ NSLog(@"创建失败"); } }</span>
=======================文件的删除==========================
//删除文件夹
1.先判断有没有要删的文件夹存在
if ([fileManger fileExistsAtPath:avPath]) { //如果存在就删除 BOOL isSuccess = [fileManger removeItemAtPath:avPath error:nil]; NSLog(@"%@",isSuccess ? @"删除成功":@"删除失败"); }
=======================文件的拷贝==========================
//把NB.plist 拷贝到 AV 文件夹下
//NSBundle 应用程序包,我们从AppStore下载的应用就是这个包
//获取应用程序包的路径
//iOS8.0 之后,**.app 单独存放在一个文件内,**.app 这个文件只能读,不能写入,最终上传到AppStore 的包就是这个包
NSString *bundlePath = [[NSBundle mainBundle]bundlePath]; NSLog(@"%@",bundlePath);
//1.获取NB.plist 的路径 NSString *nbPath = [[NSBundle mainBundle]pathForResource:@"NB.plist" ofType:nil]; //2.制造移动到沙盒Documents 文件夹下AV文件夹下NB.plist NSString *desPath = [avPath stringByAppendingPathComponent:@"NB.plist"]; //3.文件拷贝 if (![fileManger fileExistsAtPath:desPath]) { //第一个参数:copy之前的路径 //第二个参数:要拷贝到的位置 BOOL isSucess = [fileManger copyItemAtPath:nbPath toPath:desPath error:nil]; NSLog(@"%@",isSucess ? @"拷贝成功":@"拷贝失败"); }
=======================文件的移动==========================
//从AV文件夹下,移动到Library文件夹下 //1.移动之前的路径 NSString *surcePath = desPath; //2.移动之后的路径 NSString *libraryPath = [NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES)lastObject]; NSString *toPath = [libraryPath stringByAppendingPathComponent:@"NB.plist"]; //移动 if (![fileManger fileExistsAtPath:toPath]) { BOOL isSuccess = [fileManger moveItemAtPath:surcePath toPath:toPath error:nil]; NSLog(@"%@",isSuccess ? @"移动成功":@"移动失败"); } //调用简单对象的写入和读取 [self simpleObjectWritwTpFileAndFromeFile]; //调用归档和反档 [self archiverAndArchiver]; }
=======================简单对象的写入和读取==========================
//简单对象指的是:NSString ,NSDictionary,NSData以及他们的子类
//注意:集合(NSArray,NSDictionary)的元素,必须是上面的四种基本数据类型,不能放复杂对象,才能直接进行文件的写入和读取;
字符串的写入与读取:
//1.字符串的写入 NSString *string = @"小韩哥真帅"; //2.在Documents 文件夹下创建一个文件"text.text" NSString *textPath = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)lastObject] stringByAppendingPathComponent:@"text.text"]; // NSLog(@"%@",textPath); //3.字符串的写入 // 第一个参数:要写入的文件路径 // 第二个参数: YES提供多线程的安全防护,NO则不提供安全防护 // 第三个参数:编码的格式 BOOL isSuccess = [string writeToFile:textPath atomically:YES encoding:NSUTF8StringEncoding error:nil]; NSLog(@"%@",isSuccess ? @"写入成功" :@"写入失败"); //4.字符串从文件中读取数据 //第一个参数:要读取的文件路径 NSString *contentString = [NSString stringWithContentsOfFile:textPath encoding:NSUTF8StringEncoding error:nil]; NSLog(@"%@",contentString);
NSArray 的读取和写入:
//1.准备数组 NSArray *array = @[@"小韩哥",@"蔡国庆",@"周杰伦"]; //2.将数组写入到 caches 文件夹下 的array.text NSString *arrayPath = [[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES)lastObject]stringByAppendingPathComponent:@"array.text"]; //3.数组写入 数组写入后的文件是XML格式的 isSuccess = [array writeToFile:arrayPath atomically:YES]; NSLog(@"%@",isSuccess ? @"数组写入成功":@"数组写入失败"); //数组的读取 NSArray *contentArray = [NSArray arrayWithContentsOfFile:arrayPath]; NSLog(@"%@",contentArray);
NSDictionary 的写入和读取 写入之后变成xml格式:
//1.准备字典 NSDictionary *dic = @{@"男":@"小韩哥",@"明星":@"蔡国庆",@"国家主席":@"习大大"}; //2.tem 文件夹下创建一个Dictionary.text 文件 NSString *dictionaryPath = [NSTemporaryDirectory()stringByAppendingPathComponent:@"dictionary.text"]; //3.字典的写入 isSuccess = [dic writeToFile:dictionaryPath atomically:YES]; NSLog(@"%@",isSuccess ? @"字典写入成功":@"字典写入失败"); //4.字典的读取 NSDictionary *contentDic = [NSDictionary dictionaryWithContentsOfFile:dictionaryPath]; NSLog(@"%@",contentDic);
NSData 写入和读取:
NSString *dataString = @"我想对我身边人说,你该洗脚了"; //1.准备NSData 对象 NSData *data = [dataString dataUsingEncoding:NSUTF8StringEncoding]; //2.在library 中写入 data.text 文件 NSString *dataPath = [[NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES)lastObject]stringByAppendingPathComponent:@"data.text"]; //3.NSData 的写入 isSuccess = [data writeToFile:dataPath atomically:YES]; NSLog(@"%@",isSuccess ? @"NSData写入成功":@"NSData写入失败"); //4.NSData 的读取 NSData *contentData = [NSData dataWithContentsOfFile:dataPath]; //将二进制流转为字符串 NSString *newString = [[[NSString alloc]initWithData:contentData encoding:NSUTF8StringEncoding]autorelease]; NSLog(@"%@",newString);
=======================复杂对象的写入和读取==========================
复杂对象,就是Fundation 框架下不存在的数据类,也就是我们自己定义类,就叫复杂对象,复杂对象不能直接写入到文件,必须借助一些工具,NSKeyedArchiver(归档工具),读取时必须借助工具类NSKeyedUnarchiver(反归档工具)
归档和反档:
1.创建复杂对象Person
Person.h
#import <Foundation/Foundation.h> @interface Person : NSObject<NSCoding> //如果复杂对象想要完成归档和反归档,则这个对象必须遵循NSCoding协议 - (void)encodeWithCoder : (NSCoder *)aCoder; @property(nonatomic,copy)NSString *name;//姓名 @property(nonatomic,copy)NSString *gender;//性别 @property(nonatomic,assign)NSInteger age;//年龄 - (id)initWithName : (NSString *)name gender : (NSString *)gender age : (NSInteger )age; @end
Person.m
#import "Person.h" @implementation Person - (void)dealloc{ self.name = nil; self.gender = nil; [super dealloc]; } - (id)initWithName : (NSString *)name gender : (NSString *)gender age : (NSInteger )age{ if (self = [super init]) { self.name = name; self.age = age; self.gender = gender; } return self; } -(NSString *)description{ return [NSString stringWithFormat:@"%@-%@-%ld",_name,_gender,_age]; } //归档的协议方法 - (void)encodeWithCoder : (NSCoder *)aCoder{ //不止这个对象要归档,它的属性要被归档,此时要对它的属性进行编码 [aCoder encodeObject:self.name forKey:@"name"]; [aCoder encodeObject:self.gender forKey:@"gender"]; [aCoder encodeObject:@(self.age) forKey:@"age"]; } //反归档的协议方法 - (id)initWithCoder:(NSCoder *)aDecoder{ if (self = [super init]) { //解码 self.name = [aDecoder decodeObjectForKey:@"name"]; self.gender = [aDecoder decodeObjectForKey:@"gender"]; self.age = [[aDecoder decodeObjectForKey:@"age"]integerValue]; } return self; } @end
归档:
//1.创建复杂对象Person Person *p1 = [[[Person alloc]initWithName:@"小韩哥" gender:@"男" age:20]autorelease]; //2.创建归档工具 NSMutableData *data = [NSMutableData data]; NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc]initForWritingWithMutableData:data]; //3.归档 //第一个参数:要被归档的对象 //第二个参数:给归档对象一个key值,作为 标识,方便反归档的时候把它找回来 [archiver encodeObject:p1 forKey:@"boyFriend"]; //4.完成归档 [archiver finishEncoding]; //5.释放 [archiver release]; //6.将归档后的数据文件 //将文件写入到沙盒文件夹下 NSString *personPath = [NSHomeDirectory() stringByAppendingPathComponent:@"person.text"]; //7.将转化的data数据写入到文件中 BOOL isSuccess = [data writeToFile:personPath atomically:YES]; NSLog(@"%@",isSuccess ? @"写入成功":@"写入失败");
反归档:
NSData *contentData = [NSData dataWithContentsOfFile:personPath]; //1.创建反归档工具 NSKeyedUnarchiver *unArchiver = [[NSKeyedUnarchiver alloc]initForReadingWithData:contentData]; //2.读取文件(需要执行归档方法) Person *p2 = [unArchiver decodeObjectForKey:@"boyFriend"]; NSLog(@"%@",p2); //3.停止反归档 [unArchiver finishDecoding]; //4.释放 [unArchiver release];
=======================数组和复杂对象结合==========================
创建数组:
Person *p3 = [[Person alloc]initWithName:@"小美女" gender:@"女" age:21]; Person *p4 = [[Person alloc]initWithName:@"郭美美" gender:@"女" age:19]; NSArray *pArray = @[p3,p4]; [p3 release]; [p4 release];
//注意:复杂对象存入数组要想完成归档,那么存入的复杂对象必须遵循NSCoding协议
//使用归档把数组写入到文件
//1.创建归档工具 NSMutableData *aData = [NSMutableData data]; NSKeyedArchiver *nArchvier = [[NSKeyedArchiver alloc]initForWritingWithMutableData:aData]; //2.使用归档对象把数组归档 [nArchvier encodeObject:pArray forKey:@"array"]; //3.停止归档工具 [nArchvier finishEncoding]; //4.释放 [nArchvier release];
//文件写入到Documents 文件夹下,"array.tet"
NSString *arrayPath = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)lastObject]stringByAppendingPathComponent:@"array.text"]; isSuccess = [aData writeToFile:arrayPath atomically:YES]; NSLog(@"%@",isSuccess ? @"复杂数组写入成功":@"复杂数组写入失败");
//复杂数组的读取
//复杂数组的读取 NSData *newData = [NSData dataWithContentsOfFile:arrayPath]; //1.创建反归档工具 NSKeyedUnarchiver *nUnarchvier = [[NSKeyedUnarchiver alloc]initForReadingWithData:newData]; //2.通过key值将对象反归档 NSArray *newArray = [nUnarchvier decodeObjectForKey:@"array"]; //3.停止反归档工具 [nUnarchvier finishDecoding]; //4.释放 [nUnarchvier release]; NSLog(@"%@ %@",newArray[0],newArray[1]);
iOS中 数据持久化 UI高级_17的更多相关文章
-
QF——iOS中数据持久化的几种方式
数据持久化的几种方式: 一.属性列表文件: .plist文件是种XML文件.数组,字典都可以和它互相转换.数组和字典可以写入本地变成plist文件.也可以读取本地plist文件,生成数组或字典. 读取 ...
-
IOS开发中数据持久化的几种方法--NSUserDefaults
IOS开发中数据持久化的几种方法--NSUserDefaults IOS 开发中,经常会遇到需要把一些数据保存在本地的情况,那么这个时候我们有以下几种可以选择的方案: 一.使用NSUserDefaul ...
-
iphone开发中数据持久化之——属性列表序列化(一)
数据持久化是应用程序开发过程中的一个基本问题,对应用程序中的数据进行持久化存储,有多重不同的形式.本系列文章将介绍在iphone开发过程中数据持久化的三种主要形式,分别是属性列表序列号.对象归档化以及 ...
-
iOS之数据持久化方案
概论 所谓的持久化,就是将数据保存到硬盘中,使得在应用程序或机器重启后可以继续访问之前保存的数据.在iOS开发中,有很多数据持久化的方案,接下来我将尝试着介绍一下5种方案: plist文件(属性列表) ...
-
iOS的数据持久化
所谓的持久化,就是将数据保存到硬盘中,使得在应用程序或机器重启后可以继续访问之前保存的数据.在iOS开发中,有很多数据持久化的方案,接下来我将尝试着介绍一下5种方案: plist文件(属性列表) pr ...
-
IOS - 本地数据持久化
转:相对复杂的App仅靠内存的数据肯定无法满足,数据写磁盘作持久化存储是几乎每个客户端软件都需要做的.简单如“是否第一次打开”的BOOL值,大 到游戏的进度和状态等数据,都需要进行本地持久化存储.这些 ...
-
iOS - OC 数据持久化
1.Sandbox 沙箱 iOS 为每个应用提供了独立的文件空间,一个应用只能直接访问为本应用分配的文件目录,不可以访问其他目录,每个应用自己独立的访问空间被称为该应用的沙盒.也就是说,一个应用与文件 ...
-
iOS - Swift 数据持久化
1.Sandbox 沙箱 iOS 为每个应用提供了独立的文件空间,一个应用只能直接访问为本应用分配的文件目录,不可以访问其他目录,每个应用自己独立的访问空间被称为该应用的沙盒.也就是说,一个应用与文件 ...
-
IOS开发--数据持久化篇之文件存储(一)
前言:个人觉得开发人员最大的悲哀莫过于懂得使用却不明白其中的原理.在代码之前我觉得还是有必要简单阐述下相关的一些知识点. 因为文章或深或浅总有适合的人群.若有朋友发现了其中不正确的观点还望多多指出,不 ...
随机推荐
-
正则表达式在iOS中的运用
1.什么是正则表达式 正则表达式,又称正规表示法,是对字符串操作的一种逻辑公式.正则表达式可以检测给定的字符串是否符合我们定义的逻辑,也可以从字符串中获取我们想要的特定部分.它可以迅速地用极简单的方式 ...
-
Sqli-LABS通关笔录-15
这关是延时的了. Payload: -admin' or sleep(10)# 需要注意的是,--+不行反而#才可以.具体缘由可见<sql注入之你问我答>第20问:http://www.c ...
-
s:iterator间接实现跳出循环
在用s:iterator遍历小组成员时需要过滤出管理员,然后在找到第一个管理员以后停止循环,下面是我的代码: <s:set name="index" value=" ...
-
POJ3038 Flying Right
Description Figuring that they cannot do worse than the humans have, Farmer John's cows have decided ...
-
C++中的类型重定义
发现重复定义是由于从两个不同的路径包含了同一个头文件而引起的,同事也建议从另外一个路径打开工程试试, 这才慢慢发现了原因.这个原因可能有些拗口,而事实上要出现这种错误也有些"曲折" ...
-
BCP 导入导出数据库数据
使用 bcp 将数据库迁移到 Azure SQL Database --所有 都是在本机sql上运行--先开启cmdshellEXEC sp_configure 'show advanced opti ...
-
poj 1125 Stockbroker Grapevine dijkstra算法实现最短路径
点击打开链接 Stockbroker Grapevine Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 23760 Ac ...
-
Cron表达式说明
CronTrigger CronTriggers往往比SimpleTrigger更有用,如果您需要基于日历的概念,而非SimpleTrigger完全指定的时间间隔,复发的发射工作的时间表. CronT ...
-
Python生成器与yield
列表推导与生成器表达式 当我们创建了一个列表的时候,就创建了一个可以迭代的对象: >>> squares=[n*n for n in range(3)] >>> f ...
-
[2017-07-18]logstash配置示例
提醒 /etc/logstash/conf.d/下虽然可以有多个conf文件,但是Logstash执行时,实际上只有一个pipeline,它会将/etc/logstash/conf.d/下的所有con ...