NSFileManager

iOS 当中的数据一般都存放在三个目录里,Documents,Library,tmp
Documents:用户生成的文件、其他数据及其他程序不能重新创建的文件,iTunes备份和恢复的时候会包括此目录
Library:主要使用它的子文件夹,我们熟悉的NSUserDefaults就存在于它的子目录中。
Library/Caches:存放缓存文件,iTunes不会备份此目录,此目录下文件不会在应用退出删除,“删除缓存”一般指的就是清除此目录下的文件。
Library/Preferences:NSUserDefaults的数据存放于此目录下。
tmp:只是临时使用的数据,iTunes不会备份和恢复此目录,此目录下文件可能会在应用退出后删除。App应当负责在不需要使用的时候清理这些文件,系统在App不运行的时候也可能清理这个目录。

- (NSString *)getDocumetsPath {
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    return paths[0];
}

- (NSString *)getLibraryPath {
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSUserDomainMask, YES);
    return paths[0];
}

- (NSString *)getCachesPath {
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES);
    return paths[0];
}

- (NSString *)tmpPath {
    NSString *path = NSTemporaryDirectory();
    return path;
}

//创建目录

- (NSString *)createFolder:(NSString *)fileName {
    NSString *documentsPath = [self getDocumetsPath];
    NSString *folderPath = [documentsPath stringByAppendingPathComponent:fileName];
    NSFileManager *fileManager = [NSFileManager defaultManager];
    
    BOOL isEixt = NO;
    if ([fileManager fileExistsAtPath:folderPath isDirectory:&isEixt]) {//判断路径是否存在
        return folderPath;
    } else {
        BOOL isSuccess = [fileManager createDirectoryAtPath:folderPath withIntermediateDirectories:YES attributes:nil error:nil]; //创建文件路径
        if (isSuccess) {
            return folderPath;
        } else {
            return nil;
        }
    }
}

//创建文件

- (BOOL)createFile:(NSString *)filePath {
    NSString *path = [filePath stringByAppendingString:@"test.txt"];
    NSFileManager *fileManager = [NSFileManager defaultManager];
    
    BOOL isSuccess = [fileManager createFileAtPath:path contents:nil attributes:nil];
    if (isSuccess) {
        return YES;
    } else {
        return NO;
    }
}

//写入文件

- (BOOL)writeToFile:(NSString *)filePath {
    NSString *test = @"";
    BOOL isSuccess = [test writeToFile:filePath atomically:YES encoding:NSUTF8StringEncoding error:nil];
    return isSuccess;
}

//文件属性

-(void)fileAttriutes:(NSString *)filePath{
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSDictionary *fileAttributes = [fileManager attributesOfItemAtPath:filePath error:nil];
    NSArray *keys;
    id key, value;
    keys = [fileAttributes allKeys];
    NSInteger count = [keys count];
    for (NSInteger i = 0; i < count; i++) {
        key = [keys objectAtIndex: i];  //文件名
        value = [fileAttributes objectForKey: key];  //文件属性
    }
}

//删除文件路径

- (BOOL)deleteFileByPath:(NSString *)path {
    NSFileManager *fileManager = [NSFileManager defaultManager];
    
    BOOL res = [fileManager removeItemAtPath:path error:nil];
    NSLog(@"文件是否存在: %@",[fileManager isExecutableFileAtPath:path]?@"YES":@"NO");
    return res;
}

//复制文件

- (BOOL)copyFile:(NSString *)path topath:(NSString *)topath {
    BOOL result = NO;
    NSError * error = nil;
    
    result = [[NSFileManager defaultManager]copyItemAtPath:path toPath:topath error:&error ];
    
    if (error){
        NSLog(@"copy失败:%@",[error localizedDescription]);
    }
    return result;
}

//剪切移动文件

+ (BOOL)cutFile:(NSString *)path topath:(NSString *)topath {
    BOOL result = NO;
    NSError * error = nil;
    result = [[NSFileManager defaultManager]moveItemAtPath:path toPath:topath error:&error ];
    if (error){
        NSLog(@"cut失败:%@",[error localizedDescription]);
    }
    return result;
}

//得到磁盘缓存的大小

- (NSUInteger)getSize:(NSString *)filePath {
    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSUInteger size = 0;
    NSDirectoryEnumerator *fileEnumerator = [fileManager enumeratorAtPath:filePath];
    for (NSString *fileName in fileEnumerator) {
        NSString *filePaths = [filePath stringByAppendingPathComponent:fileName];
        NSDictionary<NSString *, id> *attrs = [[NSFileManager defaultManager] attributesOfItemAtPath:filePaths error:nil];
        size += [attrs fileSize];
    }
    return size;
}

//获取磁盘中文件数量

- (NSUInteger)getDiskCount:(NSString *)filePath {
    NSFileManager *fileManager = [NSFileManager defaultManager];
    __block NSUInteger count = 0;
    dispatch_sync(dispatch_queue_create("xq_test", DISPATCH_QUEUE_CONCURRENT), ^{
        NSDirectoryEnumerator *fileEnumerator = [fileManager enumeratorAtPath:filePath];
        count = fileEnumerator.allObjects.count;
    });
    return count;
}

//异步计算磁盘缓存的大小

- (void)calculateSize:(NSString *)filePath {
    NSURL *diskCacheURL = [NSURL fileURLWithPath:filePath isDirectory:YES];
    NSFileManager *fileManager = [NSFileManager defaultManager];

    dispatch_async(dispatch_queue_create("xq_test", DISPATCH_QUEUE_CONCURRENT), ^{
        NSUInteger fileCount = 0;
        NSUInteger totalSize = 0;
        
        NSDirectoryEnumerator *fileEnumerator = [fileManager enumeratorAtURL:diskCacheURL
                                                   includingPropertiesForKeys:@[NSFileSize]
                                                                      options:NSDirectoryEnumerationSkipsHiddenFiles
                                                                 errorHandler:NULL];
        for (NSURL *fileURL in fileEnumerator) {
            NSNumber *fileSize;
            [fileURL getResourceValue:&fileSize forKey:NSURLFileSizeKey error:NULL];
            totalSize += fileSize.unsignedIntegerValue;
            fileCount += 1;
        }
        NSLog(@"fileCount:%lu  totalSize:%lu",(unsigned long)fileCount,(unsigned long)totalSize);
    });
}

//异步清除所有失效的缓存图片-因为可以设定缓存时间,超过则失效

 - (void)deleteOldFilesWithCompletionBlock:(nullable SDWebImageNoParamsBlock)completionBlock {
 dispatch_async(self.ioQueue, ^{
 NSURL *diskCacheURL = [NSURL fileURLWithPath:self.diskCachePath isDirectory:YES];
 //resourceKeys数组包含遍历文件的属性,NSURLIsDirectoryKey判断遍历到的URL所指对象是否是目录,
 //NSURLContentModificationDateKey判断遍历返回的URL所指项目的最后修改时间,NSURLTotalFileAllocatedSizeKey判断URL目录中所分配的空间大小
 NSArray<NSString *> *resourceKeys = @[NSURLIsDirectoryKey, NSURLContentModificationDateKey, NSURLTotalFileAllocatedSizeKey];
 
 // This enumerator prefetches useful properties for our cache files.
 //利用目录枚举器遍历指定磁盘缓存路径目录下的文件,从而我们活的文件大小,缓存时间等信息
 NSDirectoryEnumerator *fileEnumerator = [_fileManager enumeratorAtURL:diskCacheURL
 includingPropertiesForKeys:resourceKeys
 options:NSDirectoryEnumerationSkipsHiddenFiles
 errorHandler:NULL];
 //计算过期时间,默认1周以前的缓存文件是过期失效
 NSDate *expirationDate = [NSDate dateWithTimeIntervalSinceNow:-self.config.maxCacheAge];
 //保存遍历的文件url
 NSMutableDictionary<NSURL *, NSDictionary<NSString *, id> *> *cacheFiles = [NSMutableDictionary dictionary];
 //保存当前缓存的大小
 NSUInteger currentCacheSize = 0;
 
 // Enumerate all of the files in the cache directory.  This loop has two purposes:
 //
 //  1. Removing files that are older than the expiration date.
 //  2. Storing file attributes for the size-based cleanup pass.
 //保存删除的文件url
 NSMutableArray<NSURL *> *urlsToDelete = [[NSMutableArray alloc] init];
 //遍历目录枚举器,目的1删除过期文件 2纪录文件大小,以便于之后删除使用
 for (NSURL *fileURL in fileEnumerator) {
 NSError *error;
 //获取指定url对应文件的指定三种属性的key和value
 NSDictionary<NSString *, id> *resourceValues = [fileURL resourceValuesForKeys:resourceKeys error:&error];
 
 // Skip directories and errors.
 //如果是文件夹则返回
 if (error || !resourceValues || [resourceValues[NSURLIsDirectoryKey] boolValue]) {
 continue;
 }
 
 // Remove files that are older than the expiration date;
 //获取指定url文件对应的修改日期
 NSDate *modificationDate = resourceValues[NSURLContentModificationDateKey];
 //如果修改日期大于指定日期,则加入要移除的数组里
 if ([[modificationDate laterDate:expirationDate] isEqualToDate:expirationDate]) {
 [urlsToDelete addObject:fileURL];
 continue;
 }
 
 // Store a reference to this file and account for its total size.
 //获取指定的url对应的文件的大小,并且把url与对应大小存入一个字典中
 NSNumber *totalAllocatedSize = resourceValues[NSURLTotalFileAllocatedSizeKey];
 currentCacheSize += totalAllocatedSize.unsignedIntegerValue;
 cacheFiles[fileURL] = resourceValues;
 }
 //删除所有最后修改日期大于指定日期的所有文件
 for (NSURL *fileURL in urlsToDelete) {
 [_fileManager removeItemAtURL:fileURL error:nil];
 }
 
 // If our remaining disk cache exceeds a configured maximum size, perform a second
 // size-based cleanup pass.  We delete the oldest files first.
 //如果当前缓存的大小超过了默认大小,则按照日期删除,直到缓存大小<默认大小的一半
 if (self.config.maxCacheSize > 0 && currentCacheSize > self.config.maxCacheSize) {
 // Target half of our maximum cache size for this cleanup pass.
 const NSUInteger desiredCacheSize = self.config.maxCacheSize / 2;
 
 // Sort the remaining cache files by their last modification time (oldest first).
 //根据文件创建的时间排序
 NSArray<NSURL *> *sortedFiles = [cacheFiles keysSortedByValueWithOptions:NSSortConcurrent
 usingComparator:^NSComparisonResult(id obj1, id obj2) {
 return [obj1[NSURLContentModificationDateKey] compare:obj2[NSURLContentModificationDateKey]];
 }];
 
 // Delete files until we fall below our desired cache size.
 //迭代删除缓存,直到缓存大小是默认缓存大小的一半
 for (NSURL *fileURL in sortedFiles) {
 if ([_fileManager removeItemAtURL:fileURL error:nil]) {
 NSDictionary<NSString *, id> *resourceValues = cacheFiles[fileURL];
 NSNumber *totalAllocatedSize = resourceValues[NSURLTotalFileAllocatedSizeKey];
 currentCacheSize -= totalAllocatedSize.unsignedIntegerValue;
 
 if (currentCacheSize < desiredCacheSize) {
 break;
 }
 }
 }
 }
 if (completionBlock) {
 dispatch_async(dispatch_get_main_queue(), ^{
 completionBlock();
 });
 }
 });
 }
 - (unsigned long long)fileSize;        //文件大小
 - (NSDate *)fileModificationDate;      //文件的修改时间
 - (NSString *)fileType;                //文件类型
 - (NSUInteger)filePosixPermissions;
 - (NSString *)fileOwnerAccountName;    //文件拥有者
 - (NSString *)fileGroupOwnerAccountName;
 - (NSInteger)fileSystemNumber;       
 - (NSUInteger)fileSystemFileNumber;
 - (BOOL)fileExtensionHidden;
 - (OSType)fileHFSCreatorCode;
 - (OSType)fileHFSTypeCode;
 - (BOOL)fileIsImmutable;
 - (BOOL)fileIsAppendOnly;
 - (NSDate *)fileCreationDate;        //创建时间
 - (NSNumber *)fileOwnerAccountID;
 - (NSNumber *)fileGroupOwnerAccountID;
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 214,444评论 6 496
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,421评论 3 389
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 160,036评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,363评论 1 288
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,460评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,502评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,511评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,280评论 0 270
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,736评论 1 307
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,014评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,190评论 1 342
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,848评论 5 338
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,531评论 3 322
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,159评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,411评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,067评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,078评论 2 352

推荐阅读更多精彩内容