zoukankan      html  css  js  c++  java
  • OC中文件的操作

    OC中文件操作,在之前的文章中,已经接触到了文件的创建了,但是那不是很具体和详细,这篇文章我们就来仔细看一下OC中是如何操作文件的:


    第一、首先来看一下本身NSString类给我们提供了哪些可以操作文件路径名的方法
    [objc]  view plaincopy  
    8.   
    9. #import <Foundation/Foundation.h>  
    10.   
    11. int main(int argc, const charchar * argv[]) {  
    12.     @autoreleasepool {  
    13.           
    14.         //演示路径  
    15.         NSString *path = @"/Users/jiangwei/file.text";  
    16.           
    17.         //1.返回路径的组成部分  
    18.         NSArray *array = [path pathComponents];  
    19.         NSLog(@"%@",array);  
    20.           
    21.         //2.返回路径最后组成部分  
    22.         NSString *str = [path lastPathComponent];  
    23.         NSLog(@"%@",str);  
    24.           
    25.         //3.在原有的路径后面追加子目录  
    26.         //这种方式有一点不好,就是需要添加/  
    27.         [path stringByAppendingString:@"/appFile.text"];  
    28.         //不需要添加/  
    29.         [path stringByAppendingPathComponent:@"appFile.text"];  
    30.           
    31.         //4.删除最后的组成部分  
    32.         str = [path stringByDeletingLastPathComponent];  
    33.         //删除扩展名(.text被删除了)  
    34.         str = [path stringByDeletingPathExtension];  
    35.           
    36.         //5.获取扩展名  
    37.         str = [path pathExtension];  
    38.           
    39.         //6.添加扩展名  
    40.         [path stringByAppendingPathExtension:@".jpg"];  
    41.           
    42.     }  
    43.     return 0;  
    44. }  
    在Java中,我们知道,当我们去操作一个文件的时候,最开始的时候肯定要去构建一个路径,这个路径一般都是String类型的,我们需要定义不同的路径和文件名,OC中也不例外,不过OC中的NSString类在这方面做的可能会更好,下面依次来看一下他的方法:
    1、将路径进行分割
    [java]  view plaincopy 
    1. //演示路径  
    2. NSString *path = @"/Users/jiangwei/file.text";  
    3.   
    4. //1.返回路径的组成部分  
    5. NSArray *array = [path pathComponents];  
    6. NSLog(@"%@",array);  
    运行结果:

    返回的一个数组,将路径分割了,但是需要注意的是,第一个是"/",这个也算是路径的一部分。


    2、返回路径的最后组成部分
    [objc]  view plaincopy 
    1. //2.返回路径最后组成部分  
    2. NSString *str = [path lastPathComponent];  
    3. NSLog(@"%@",str);  
    运行结果:

    这个直接返回路径的最后一部分,这个如果放在Java中,我们可能需要用到String类的字符串分割技术了,没有这里的方便


    3、添加子目录/子文件
    [objc]  view plaincopy 
    1. //3.在原有的路径后面追加子目录  
    2. //这种方式有一点不好,就是需要添加/  
    3. //演示路径  
    4. str = [path stringByAppendingString:@"/appFile.text"];  
    5. NSLog(@"%@",str);  
    6. //不需要添加/  
    7. str = [path stringByAppendingPathComponent:@"appFile.text"];  
    8. NSLog(@"%@",str);  
    这里其实有两种方式可以添加,第一种是直接使用拼接字符串的方式,但是需要手动的添加"/",第二种方式是NSString提供的,不需要手动的添加"/"
    运行结果:


    4、删除最后面的部分和后缀名
    [objc]  view plaincopy 
    1. //4.删除最后的组成部分  
    2. str = [path stringByDeletingLastPathComponent];  
    3. NSLog(@"%@",str);  
    4. //删除扩展名(.text被删除了)  
    5. str = [path stringByDeletingPathExtension];  
    6. NSLog(@"%@",str);  
    运行结果:


    5、获取扩展名
    [objc]  view plaincopy 
    1. //5.获取扩展名  
    2. str = [path pathExtension];  
    3. NSLog(@"%@",str);  
    运行结果:


    6、添加扩展名
    [objc]  view plaincopy 
    1. //6.添加扩展名  
    2. str = [path stringByAppendingPathExtension:@"jpg"];  
    3. NSLog(@"%@",str);  
    运行结果:


    上面就是总结了NSString类中操作文件路径的一些方法,其实这些操作如果放在Java中做的话,就是需要使用String的分割,拼接等技术了。这里看到OC给我们提供了便捷


    第二、在来看一下操作文件之前需要了解的一个对象:NSData
    这个类的作用就是将我们写入到文件中的数据进行编码和解码操作
    [objc]  view plaincopy 
    1. //  
    2. //  main.m  
    3. //  38_NSData  
    4. //  
    5. //  Created by jiangwei on 14-10-13.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <Foundation/Foundation.h>  
    10.   
    11. //NSData类型  
    12. //是一种存储形式  
    13. int main(int argc, const charchar * argv[]) {  
    14.     @autoreleasepool {  
    15.         //存储是有编码方式的,编程字节码  
    16.         //相当于Java中的解码和编码  
    17.         NSString *s = @"tsdfsdfsdfsdf";  
    18.         NSData *data = [s dataUsingEncoding:NSUTF8StringEncoding];  
    19.         s = [[NSString alloc] initWithData:data encoding:(NSUTF8StringEncoding)];  
    20.           
    21.         //可变对象 NSMutableData 可以追加数据  
    22.     }  
    23.     return 0;  
    24. }  
    这个和Java中String直接在构造的时候就可以进行编码和解码了,这里需要使用中间类NSData,当然这个类是不可变的,如果想追加内容的话,需要使用NSMutableData类


    第三、说完了NSData这个中间类,下面来正式说文件的操作了
    但是这里对文件的操作,我们放到IOS平台去操作,因为我们后面也是会介绍IOS中文件的操作,所以就直接在这里说了,当然这里的知识会有点冲突,但是我们不关心IOS中的其他技术,只看他的文件操作:
    1、沙盒文件
    在IOS中,每个应用程序都是一个沙盒,他们有自己的文件目录,这个目录对其他程序是不可见的,和Android中的/data/data/包名/中的内容差不多,当然IOS中的沙盒目录有三种:
    Documents:存放长期使用的文件(一般存放目录)
    Library:系统存放文件
    tmp:临时文件,app重启时,该目录下得文件清空
    下面来看一个简单的例子吧:
    [objc]  view plaincopy 
    1. //  
    2. //  main.m  
    3. //  36_SandBoxFile  
    4. //  
    5. //  Created by jiangwei on 14-10-13.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <UIKit/UIKit.h>  
    10. #import "AppDelegate.h"  
    11.   
    12. int main(int argc, charchar * argv[]) {  
    13.     @autoreleasepool {  
    14.         //获取沙盒目录  
    15.         //默认有三个文件夹  
    16.         //Documents:存放长期使用的文件(一般存放目录)  
    17.         //Library:系统存放文件  
    18.         //tmp:临时文件,app重启时,该目录下得文件清空  
    19.           
    20.         //第一种获取方式,我们得到Home目录之后,手动的去拼接Document/Library  
    21.         NSString *homePath = NSHomeDirectory();  
    22.         NSLog(@"沙盒目录:%@",homePath);  
    23.           
    24.         //第二种方式,直接使用Api获取  
    25.         //NSDocumentDirectory:Documents文件夹  
    26.         //NSLibraryDirectory:Library文件夹  
    27.         NSArray *array = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);  
    28.         NSLog(@"%@",array);  
    29.           
    30.         NSArray *array1 = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);  
    31.         NSLog(@"%@",array1);  
    32.           
    33.         return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));  
    34.     }  
    35. }  
    创建IOS项目和OC差不多:
    后续的操作就一样了,创建完之后的项目结构:

    我们在main.m文件中写我们的代码就可以了。

    下面来看代码:
    [java]  view plaincopy 
    1. //第一种获取方式,我们得到Home目录之后,手动的去拼接Document/Library  
    2. NSString *homePath = NSHomeDirectory();  
    3. NSLog(@"沙盒目录:%@",homePath);  
    获取沙盒的home目录,然后我们可以操作在其下面创建子目录了

    这里有两种方式去创建Document等目录,一种是我们用上面NSString类提供的方法去手动拼接目录
    还有一种是用系统给我们提供的方法,这两种都是可以的
    [java]  view plaincopy 
    1. //第二种方式,直接使用Api获取  
    2. //NSDocumentDirectory:Documents文件夹  
    3. //NSLibraryDirectory:Library文件夹  
    4. NSArray *array = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);  
    5. NSLog(@"%@",array);  
    6.           
    7. NSArray *array1 = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);  
    8. NSLog(@"%@",array1);  

    看一下运行结果:



    第四、了解了程序的沙盒目录,下面继续来看一下操作文件的两个类
    一、NSFileManager
    这个类的主要功能是对文件进行操作:创建,复制,剪切,删除等
    看代码:
    [objc]  view plaincopy 
    1. //  
    2. //  main.m  
    3. //  39_NSFileManager  
    4. //  
    5. //  Created by jiangwei on 14-10-13.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <UIKit/UIKit.h>  
    10. #import "AppDelegate.h"  
    11.   
    12. //NSFileManager:对文件进行操作的,包括复制,粘贴,删除,剪切等操作  
    13. int main(int argc, charchar * argv[]) {  
    14.     @autoreleasepool {  
    15.           
    16.         //------------------创建文件/文件夹  
    17.         //获取沙盒目录  
    18.         NSString *homePath = NSHomeDirectory();  
    19.         //在沙盒目录中创建一个文件file.text  
    20.         NSString *filePath = [homePath stringByAppendingPathComponent:@"Documents/file.text"];  
    21.         //NSFileManager是单利模式,所以不能使用alloc+init创建  
    22.         NSFileManager *manager = [NSFileManager defaultManager];  
    23.         NSString *str = @"无线互联";  
    24.         NSData *data = [str dataUsingEncoding:NSUTF8StringEncoding];  
    25.         //参数:文件路径、文件内容、文件的属性  
    26.         BOOL sucess = [manager createFileAtPath:filePath contents:data attributes:nil];  
    27.         if(sucess){  
    28.             NSLog(@"文件创建成功");  
    29.         }else{  
    30.             NSLog(@"文件创建失败");  
    31.         }  
    32.           
    33.         //创建文件夹  
    34.         NSString *filePaths = [homePath stringByAppendingPathComponent:@"Documents/file"];  
    35.         NSError *error;  
    36.         //需要传递一个创建失败的指针对象,记录创建失败的信息  
    37.         BOOL success1 = [manager createDirectoryAtPath:filePaths withIntermediateDirectories:YES attributes:nil error:&error];  
    38.         if(!success1){  
    39.             NSLog(@"创建成功");  
    40.         }else{  
    41.             NSLog(@"创建失败");  
    42.         }  
    43.           
    44.           
    45.         //--------------------读取文件  
    46.         //根据路径读取文件内容  
    47.         NSData *datas = [manager contentsAtPath:filePath];  
    48.         NSString *s = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];  
    49.         NSLog(@"%@",s);  
    50.           
    51.           
    52.         //--------------------移动文件/剪切文件  
    53.         //NSFileManager中没有提供重命名的方法,所以我们可以借助移动的api进行操作  
    54.         //把filePath移动到targetPath目录中  
    55.         NSString *targetPath = [homePath stringByAppendingPathComponent:@"Documents/file/file2.text"];  
    56.         BOOL sucess2 = [manager moveItemAtPath:filePath toPath:targetPath error:nil];  
    57.         if(sucess2) {  
    58.             NSLog(@"移动成功");  
    59.         }else{  
    60.             NSLog(@"移动失败");  
    61.         }  
    62.           
    63.           
    64.         //--------------------复制文件  
    65.         BOOL sucess3 = [manager copyItemAtPath:filePath toPath:targetPath error:nil];  
    66.         if(sucess3){  
    67.             //复制成功  
    68.         }else{  
    69.             //复制失败  
    70.         }  
    71.           
    72.           
    73.         //--------------------删除文件  
    74.         //删除之前需要判断这个文件是否存在  
    75.         BOOL isExist = [manager fileExistsAtPath:filePath];//判断文件是否存在  
    76.         if(isExist){  
    77.             BOOL sucess4 = [manager removeItemAtPath:filePath error:nil];  
    78.             if(sucess4){  
    79.                 //删除成功  
    80.             }else{  
    81.                 //删除失败  
    82.             }  
    83.         }  
    84.           
    85.           
    86.         //--------------------获取文件的属性  
    87.         NSDictionary *dic = [manager attributesOfItemAtPath:filePath error:nil];  
    88.         NSLog(@"%@",dic);//通过打印我们就可以查看文件属性的一些key  
    89.           
    90.         return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));  
    91.     }  
    92. }  


    1、创建文件
    [objc]  view plaincopy 
    1. //------------------创建文件/文件夹  
    2. //获取沙盒目录  
    3. NSString *homePath = NSHomeDirectory();  
    4. //在沙盒目录中创建一个文件file.text  
    5. NSString *filePath = [homePath stringByAppendingPathComponent:@"Documents/file.text"];  
    6. //NSFileManager是单利模式,所以不能使用alloc+init创建  
    7. NSFileManager *manager = [NSFileManager defaultManager];  
    8. NSString *str = @"无线互联";  
    9. NSData *data = [str dataUsingEncoding:NSUTF8StringEncoding];  
    10. //参数:文件路径、文件内容、文件的属性  
    11. BOOL sucess = [manager createFileAtPath:filePath contents:data attributes:nil];  
    12. if(sucess){  
    13.     NSLog(@"文件创建成功");  
    14. }else{  
    15.     NSLog(@"文件创建失败");  
    16. }  
    NSFileManager内部使用了单例模式,这个后面会说到OC中得单例模式,然后就是构建一个NSData类,最后使用createFileAtPath方法创建文件,不过最后的attributes参数一般是用来给这个文件定义一些属性的,当然文件本身也是有很多默认的属性,比如文件的大小,文件的创建日期等,我们也可以自己在追加一些属性。


    2、创建文件夹
    [java]  view plaincopy 
    1. //创建文件夹  
    2. NSString *filePaths = [homePath stringByAppendingPathComponent:@"Documents/file"];  
    3. NSError *error;  
    4. //需要传递一个创建失败的指针对象,记录创建失败的信息  
    5. BOOL success1 = [manager createDirectoryAtPath:filePaths withIntermediateDirectories:YES attributes:nil error:&error];  
    6. if(!success1){  
    7.     NSLog(@"创建成功");  
    8. }else{  
    9.     NSLog(@"创建失败");  
    10. }  
    从这两个操作看出来,他和Java中的File类很相似的


    3、读取文件
    [java]  view plaincopy 
    1. //--------------------读取文件  
    2. //根据路径读取文件内容  
    3. NSData *datas = [manager contentsAtPath:filePath];  
    4. NSString *s = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];  
    5. NSLog(@"%@",s);  


    4、剪切文件
    [objc]  view plaincopy 
    1. //--------------------移动文件/剪切文件  
    2. //NSFileManager中没有提供重命名的方法,所以我们可以借助移动的api进行操作  
    3. //把filePath移动到targetPath目录中  
    4. NSString *targetPath = [homePath stringByAppendingPathComponent:@"Documents/file/file2.text"];  
    5. BOOL sucess2 = [manager moveItemAtPath:filePath toPath:targetPath error:nil];  
    6. if(sucess2) {  
    7.     NSLog(@"移动成功");  
    8. }else{  
    9.     NSLog(@"移动失败");  
    10. }  
    这里有两个参数:一个是需要移动文件的路径,和需要移动到哪的路径


    5、复制文件
    [objc]  view plaincopy 
    1. //--------------------复制文件  
    2. BOOL sucess3 = [manager copyItemAtPath:filePath toPath:targetPath error:nil];  
    3. if(sucess3){  
    4.     //复制成功  
    5. }else{  
    6.     //复制失败  
    7. }  

    6、删除文件
    [objc]  view plaincopy 
    1. //--------------------删除文件  
    2. //删除之前需要判断这个文件是否存在  
    3. BOOL isExist = [manager fileExistsAtPath:filePath];//判断文件是否存在  
    4. if(isExist){  
    5.     BOOL sucess4 = [manager removeItemAtPath:filePath error:nil];  
    6.     if(sucess4){  
    7.         //删除成功  
    8.     }else{  
    9.         //删除失败  
    10.     }  
    11. }  

    7、操作文件的属性

    [objc]  view plaincopy 
    1. //--------------------获取文件的属性  
    2. NSDictionary *dic = [manager attributesOfItemAtPath:filePath error:nil];  
    3. NSLog(@"%@",dic);//通过打印我们就可以查看文件属性的一些key  
    属性一般是NSDictionary


    二、NSFileHandle
    这个类主要是对文件进行读写操作的
    看代码:
    [objc]  view plaincopy 
    1. //  
    2. //  main.m  
    3. //  40_NSFileHandle  
    4. //  
    5. //  Created by jiangwei on 14-10-13.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <UIKit/UIKit.h>  
    10. #import "AppDelegate.h"  
    11.   
    12. //写文件,我们之前使用各种数据结构来存储数据:NSString,NSData,NSDictionary,NSArray等,他们都是有一个writeToFile方法用来写文件的  
    13.   
    14. //纯文本:没有任何格式的数据  
    15. //非纯文本:有修饰的数据(字体大小,字体颜色等)  
    16.   
    17. //数组只能将如下类型写入文件,如果包含其他对象,将写入失败:NSNumber,NSString,NSData,NSDate,NSArray,NSDictionary  
    18. //数组、字典写入的文件叫做属性文件,可以使用xcode进行编辑  
    19. int main(int argc, charchar * argv[]) {  
    20.     @autoreleasepool {  
    21.           
    22.         //1.-------------------字符串读写文件  
    23.         NSString *str = @"无线互联";  
    24.         NSString *homePath = NSHomeDirectory();  
    25.         NSString *filePath = [homePath stringByAppendingPathComponent:@"Documents/file.text"];  
    26.         //现在有这样的场景,第一次把字符串写入到文件中,当我们修改字符串之后,再次写入的时候,但是可能会写入失败  
    27.         //但是之前的内容也有可能丢失,因为每次在写入新的内容的时候,会剪切之前的内容,所以这里就有可能新的没有写  
    28.         //成功,旧的文件也丢失了  
    29.         //所以这时候atomically参数:  
    30.         //YES:会将新内容先写入到一个缓存文件中,如果写入缓存成功之后,这时候就将这个缓存文件替换旧文件,这样就很安全了  
    31.         BOOL sucess = [str writeToFile:filePath atomically:YES encoding:NSUTF8StringEncoding error:nil];  
    32.         if(sucess){  
    33.             //写入成功  
    34.         }else{  
    35.             //写入失败  
    36.         }  
    37.         //读取文件内容到字符串中  
    38.         //类方法  
    39.         NSString *str1 = [NSString stringWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:nil];  
    40.         //构造方法  
    41.         //str1 = [[NSString alloc] initWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:nil];  
    42.         NSLog(@"%@",str1);  
    43.           
    44.           
    45.         //2.--------------------NSData读写  
    46.         //创建NSData的同时读取文件中的内容  
    47.         NSData *data = [[NSData alloc] initWithContentsOfFile:filePath];  
    48.         //NSData转化成NSString  
    49.         NSString *s = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];  
    50.         NSLog(@"%@",s);  
    51.           
    52.         //写文件  
    53.         BOOL sucess1 = [data writeToFile:filePath atomically:YES];  
    54.         if(sucess1){  
    55.             //写入成功  
    56.         }else{  
    57.             //写入失败  
    58.         }  
    59.           
    60.           
    61.         //3.--------------------NSArray读写文件  
    62.         NSArray *array = @[@"zhangsan",@"lisi"];  
    63.         //属性文件一般后缀名为.plist  
    64.         NSString *filePaths = [homePath stringByAppendingPathComponent:@"Documents/array.plist"];  
    65.         BOOL sucess2 = [array writeToFile:filePaths atomically:YES];  
    66.         if(sucess2){  
    67.             //写入成功  
    68.         }else{  
    69.             //写入失败  
    70.         }  
    71.         //读文件  
    72.         NSArray *arrays = [[NSArray alloc] initWithContentsOfFile:filePath];  
    73.         NSLog(@"%@",arrays);  
    74.           
    75.           
    76.         //4.---------------------NSDictionary读写文件  
    77.         NSDictionary *dic = @{@"zhang":@"zhangsan",@"li":@"lisi"};  
    78.         BOOL sucess3 = [dic writeToFile:filePath atomically:YES];  
    79.         if(sucess3){  
    80.             //写入成功  
    81.         }else{  
    82.             //写入失败  
    83.         }  
    84.           
    85.         //读文件  
    86.         dic = [[NSDictionary alloc] initWithContentsOfFile:filePath];  
    87.         NSLog(@"%@",dic);  
    88.           
    89.           
    90.         return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));  
    91.     }  
    92. }  
    这个类就和Java中的FileInputStream/FileOutputStream类似了
    其实我们在之前看到归档和解档操作的时候,那就是相当于写文件和读文件操作了。


    1、字符串直接写入文件
    [objc]  view plaincopy 
    1. //1.-------------------字符串读写文件  
    2. NSString *str = @"无线互联";  
    3. NSString *homePath = NSHomeDirectory();  
    4. NSString *filePath = [homePath stringByAppendingPathComponent:@"Documents/file.text"];  
    5. //现在有这样的场景,第一次把字符串写入到文件中,当我们修改字符串之后,再次写入的时候,但是可能会写入失败  
    6. //但是之前的内容也有可能丢失,因为每次在写入新的内容的时候,会剪切之前的内容,所以这里就有可能新的没有写  
    7. //成功,旧的文件也丢失了  
    8. //所以这时候atomically参数:  
    9. //YES:会将新内容先写入到一个缓存文件中,如果写入缓存成功之后,这时候就将这个缓存文件替换旧文件,这样就很安全了  
    10. BOOL sucess = [str writeToFile:filePath atomically:YES encoding:NSUTF8StringEncoding error:nil];  
    11. if(sucess){  
    12.     //写入成功  
    13. }else{  
    14.     //写入失败  
    15. }  
    16. //读取文件内容到字符串中  
    17. //类方法  
    18. NSString *str1 = [NSString stringWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:nil];  
    19. //构造方法  
    20. //str1 = [[NSString alloc] initWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:nil];  
    21. NSLog(@"%@",str1);  
    我们使用拼接的方式创建Documents目录中的file.text文件,然后将字符串内容写入到其中。
    writeToFile方法进行写入
    其实OC中的各种数据结构都有这个方法的:NSString,NSData,NSArray,NSSet,NSDirctionary等
    这里有两点要注意的:
    1)
    数组只能将如下类型写入文件,如果包含其他对象,将写入失败:NSNumber,NSString,NSData,NSDate,NSArray,NSDictionary
    数组、字典写入的文件叫做属性文件,可以使用xcode进行编辑

    这个就是系统提供的一个属性文件:info.plist
    这个和Java中的Property文件很类似

    2)writeToFile方法的第一个参数:automically
    现在有这样的场景,第一次把字符串写入到文件中,当我们修改字符串之后,再次写入的时候,但是可能会写入失败但是之前的内容也有可能丢失,因为每次在写入新的内容的时候,会剪切之前的内容,所以这里就有可能新的没有写成功,旧的文件也丢失了所以这时候atomically参数:YES:会将新内容先写入到一个缓存文件中,如果写入缓存成功之后,这时候就将这个缓存文件替换旧文件,这样就很安全了

    2NSData的内容读写
    [objc]  view plaincopy 
    1. //2.--------------------NSData读写  
    2. //创建NSData的同时读取文件中的内容  
    3. NSData *data = [[NSData alloc] initWithContentsOfFile:filePath];  
    4. //NSData转化成NSString  
    5. NSString *s = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];  
    6. NSLog(@"%@",s);  
    7.   
    8. //写文件  
    9. BOOL sucess1 = [data writeToFile:filePath atomically:YES];  
    10. if(sucess1){  
    11.     //写入成功  
    12. }else{  
    13.     //写入失败  
    14. }  

    3NSArray的内容读写
    [objc]  view plaincopy 
    1. //3.--------------------NSArray读写文件  
    2. NSArray *array = @[@"zhangsan",@"lisi"];  
    3. //属性文件一般后缀名为.plist  
    4. NSString *filePaths = [homePath stringByAppendingPathComponent:@"Documents/array.plist"];  
    5. BOOL sucess2 = [array writeToFile:filePaths atomically:YES];  
    6. if(sucess2){  
    7.     //写入成功  
    8. }else{  
    9.     //写入失败  
    10. }  
    11. //读文件  
    12. NSArray *arrays = [[NSArray alloc] initWithContentsOfFile:filePath];  
    13. NSLog(@"%@",arrays);  

    4NSDirctionary的内容读写
    [objc]  view plaincopy 
    1. //4.---------------------NSDictionary读写文件  
    2. NSDictionary *dic = @{@"zhang":@"zhangsan",@"li":@"lisi"};  
    3. BOOL sucess3 = [dic writeToFile:filePath atomically:YES];  
    4. if(sucess3){  
    5.     //写入成功  
    6. }else{  
    7.     //写入失败  
    8. }  
    9.   
    10. //读文件  
    11. dic = [[NSDictionary alloc] initWithContentsOfFile:filePath];  
    12. NSLog(@"%@",dic);  
    上面说到的系统的info.plist文件就是NSDirctionary


    三、在来看一下NSFileHandle的其他用法
    [objc]  view plaincopy 
    1. //  
    2. //  main.m  
    3. //  41_NSFileHandleTest  
    4. //  
    5. //  Created by jiangwei on 14-10-14.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <UIKit/UIKit.h>  
    10. #import "AppDelegate.h"  
    11.   
    12. //NSFileHandle是对文件内容进行读写  
    13. int main(int argc, charchar * argv[]) {  
    14.     @autoreleasepool {  
    15.           
    16.         //追加数据  
    17.         NSString *str = @"无线互联";  
    18.         NSString *homePath = NSHomeDirectory();  
    19.         NSString *filePath = [homePath stringByAppendingPathComponent:@"file.test"];  
    20.         [str writeToFile:filePath atomically:YES encoding:NSUTF8StringEncoding error:nil];//写入文件  
    21.           
    22.         NSFileHandle *handle = [NSFileHandle fileHandleForWritingAtPath:filePath];  
    23.         //默认是从开始位置写,所以我们需要将写入游标设置到尾部  
    24.         //从文件的末尾写入  
    25.         [handle seekToEndOfFile];  
    26.         NSString *s = @"123";  
    27.         NSData *data = [s dataUsingEncoding:NSUTF8StringEncoding];  
    28.         [handle writeData:data];  
    29.         //关闭文件  
    30.         [handle closeFile];  
    31.           
    32.           
    33.         //读取文件  
    34.         NSFileHandle *handles = [NSFileHandle fileHandleForReadingAtPath:filePath];  
    35.           
    36.         //获取文件的大小  
    37.         NSFileManager *fileManager = [NSFileManager defaultManager];  
    38.         NSDictionary *fileAttr = [fileManager attributesOfItemAtPath:filePath error:nil];  
    39.         NSNumber *fileSize = [fileAttr objectForKey:NSFileSize];  
    40.         long long sizeValue = [fileSize longLongValue];  
    41.           
    42.         //设置偏移量  
    43.         [handle seekToFileOffset:sizeValue/2];//将偏移量设置到中间位置  
    44.         //从当前偏移量读到文件末尾  
    45.         NSData *datas = [handle readDataToEndOfFile];  
    46.         NSString *s2 = [[NSString alloc] initWithData:datas encoding:NSUTF8StringEncoding];  
    47.         NSLog(@"%@",s2);  
    48.           
    49.         //一个汉字占用两个字节,有时候可能会将一个汉字分成两半,有乱码的问题,需要注意  
    50.           
    51.           
    52.         //实现复制文件的功能  
    53.         //使用NSFileHandle只能读写已经存在的文件,不能创建文件,创建文件应该使用NSFileManager  
    54.         NSString *targetPath = [homePath stringByAppendingPathComponent:@"files.test"];  
    55.         NSFileManager *fileManagers = [NSFileManager defaultManager];  
    56.         [fileManagers createFileAtPath:targetPath contents:nil attributes:nil];  
    57.           
    58.         //创建读取文件的handle  
    59.         NSFileHandle *readHandles = [NSFileHandle fileHandleForReadingAtPath:filePath];  
    60.         //创建写文件的handle  
    61.         NSFileHandle *writeHandles = [NSFileHandle fileHandleForWritingAtPath:targetPath];  
    62.           
    63.         //从当前偏移量读取到文件的末尾  
    64.         NSData *datass = [readHandles readDataToEndOfFile];  
    65.         //还有一种方式读取文件,既可以读取文件,也可以读流,功能更强  
    66.         //[readHandles availableData];  
    67.         [writeHandles writeData:datass];  
    68.           
    69.         //关闭文件  
    70.         [readHandles closeFile];  
    71.         [writeHandles closeFile];  
    72.           
    73.         //这里有问题,就是读取文件的时候全部读取了,这样会很占内存的,所以我们应该将读取内容进行分段  
    74.           
    75.           
    76.           
    77.                                  
    78.         return UIApplicationMain(argc, argv, nil, NSStringFromClass([AppDelegate class]));  
    79.     }  
    80. }  

    1、对原有的内容进行追加操作
    [objc]  view plaincopy 
    1. //追加数据  
    2. NSString *str = @"无线互联";  
    3. NSString *homePath = NSHomeDirectory();  
    4. NSString *filePath = [homePath stringByAppendingPathComponent:@"file.test"];  
    5. [str writeToFile:filePath atomically:YES encoding:NSUTF8StringEncoding error:nil];//写入文件  
    6.   
    7. NSFileHandle *handle = [NSFileHandle fileHandleForWritingAtPath:filePath];  
    8. //默认是从开始位置写,所以我们需要将写入游标设置到尾部  
    9. //从文件的末尾写入  
    10. [handle seekToEndOfFile];  
    11. NSString *s = @"123";  
    12. NSData *data = [s dataUsingEncoding:NSUTF8StringEncoding];  
    13. [handle writeData:data];  
    14. //关闭文件  
    15. [handle closeFile];  
    记得操作完之后,关闭文件,我们在追加文件的时候,只要在将当前游标移动到文件的末尾处即可,默认是在开始处

    2、读取文件的任何位置内容
    [objc]  view plaincopy 
    1. //读取文件  
    2. NSFileHandle *handles = [NSFileHandle fileHandleForReadingAtPath:filePath];  
    3.   
    4. //获取文件的大小  
    5. NSFileManager *fileManager = [NSFileManager defaultManager];  
    6. NSDictionary *fileAttr = [fileManager attributesOfItemAtPath:filePath error:nil];  
    7. NSNumber *fileSize = [fileAttr objectForKey:NSFileSize];  
    8. long long sizeValue = [fileSize longLongValue];  
    9.   
    10. //设置偏移量  
    11. [handle seekToFileOffset:sizeValue/2];//将偏移量设置到中间位置  
    12. //从当前偏移量读到文件末尾  
    13. NSData *datas = [handle readDataToEndOfFile];  
    14. NSString *s2 = [[NSString alloc] initWithData:datas encoding:NSUTF8StringEncoding];  
    15. NSLog(@"%@",s2);  
    还是设置一下游标的位置即可

    3、实现文件的复制功能
    [objc]  view plaincopy 
    1. //实现复制文件的功能  
    2. //使用NSFileHandle只能读写已经存在的文件,不能创建文件,创建文件应该使用NSFileManager  
    3. NSString *targetPath = [homePath stringByAppendingPathComponent:@"files.test"];  
    4. NSFileManager *fileManagers = [NSFileManager defaultManager];  
    5. [fileManagers createFileAtPath:targetPath contents:nil attributes:nil];  
    6.   
    7. //创建读取文件的handle  
    8. NSFileHandle *readHandles = [NSFileHandle fileHandleForReadingAtPath:filePath];  
    9. //创建写文件的handle  
    10. NSFileHandle *writeHandles = [NSFileHandle fileHandleForWritingAtPath:targetPath];  
    11.   
    12. //从当前偏移量读取到文件的末尾  
    13. NSData *datass = [readHandles readDataToEndOfFile];  
    14. //还有一种方式读取文件,既可以读取文件,也可以读流,功能更强  
    15. //[readHandles availableData];  
    16. [writeHandles writeData:datass];  
    17.   
    18. //关闭文件  
    19. [readHandles closeFile];  
    20. [writeHandles closeFile];  
    21.   
    22. //这里有问题,就是读取文件的时候全部读取了,这样会很占内存的,所以我们应该将读取内容进行分段  
    这里的这种方式是:直接将源文件内容全部读取出来,然后写入到目标文件中,这样做有一个坏处,如果这个文件的内容太大,那么一次读取出那么多内容,内存会爆的,所以应该采用分段读取,这个就用到了上面说到的读取文件的任意位置的内容

    总结
    这一篇主要是介绍了文件的操作,对于文件的操作,后面的IOS开发过程中会经常用到,所以也是一个重点,当然还有一点需要说明的是,OC中的文件操作比Java中的文件操作方便多了。
  • 相关阅读:
    好好的Timer居然有坑?
    你竟然用Integer作为synchronized的锁对象?
    是时候了解Java Socket底层实现了
    带你了解MyBatis一二级缓存
    Java利用反射排序
    用代码移动桌面图标(贪吃蛇)
    servlet上传文件+上传进度显示
    简书导航栏实现
    iPhone手机屏幕尺寸(分辨率)
    iOS深拷贝浅拷贝
  • 原文地址:https://www.cnblogs.com/GhostKZShadow/p/5105174.html
Copyright © 2011-2022 走看看