在Objective-C/cocoa中创建文件夹/目录

pro*_*eek 44 directory cocoa objective-c

我有这个代码用于在Objective-C/cocoa中创建文件夹/目录.

if(![fileManager fileExistsAtPath:directory isDirectory:&isDir])
        if(![fileManager createDirectoryAtPath:directory attributes:nil])
            NSLog(@"Error: Create folder failed %@", directory);
Run Code Online (Sandbox Code Playgroud)

它工作正常,但我得到了creatDirectoryAtPath:attributes is deprecated警告信息.在Cocoa/Objective-c中制作目录构建器的最新方法是什么?

解决了

BOOL isDir;
NSFileManager *fileManager= [NSFileManager defaultManager]; 
if(![fileManager fileExistsAtPath:directory isDirectory:&isDir])
    if(![fileManager createDirectoryAtPath:directory withIntermediateDirectories:YES attributes:nil error:NULL])
        NSLog(@"Error: Create folder failed %@", directory);
Run Code Online (Sandbox Code Playgroud)

Mat*_*att 19

您的解决方案是正确的,但Apple在其中包含一个重要说明NSFileManager.h:

/* The following methods are of limited utility. Attempting to predicate behavior 
based on the current state of the filesystem or a particular file on the 
filesystem is encouraging odd behavior in the face of filesystem race conditions. 
It's far better to attempt an operation (like loading a file or creating a 
directory) and handle the error gracefully than it is to try to figure out ahead 
of time whether the operation will succeed. */

- (BOOL)fileExistsAtPath:(NSString *)path;
- (BOOL)fileExistsAtPath:(NSString *)path isDirectory:(BOOL *)isDirectory;
- (BOOL)isReadableFileAtPath:(NSString *)path;
- (BOOL)isWritableFileAtPath:(NSString *)path;
- (BOOL)isExecutableFileAtPath:(NSString *)path;
- (BOOL)isDeletableFileAtPath:(NSString *)path;
Run Code Online (Sandbox Code Playgroud)

实质上,如果多个线程/进程同时修改文件系统,则状态可能会在调用fileExistsAtPath:isDirectory:和调用之间发生变化createDirectoryAtPath:withIntermediateDirectories:,因此fileExistsAtPath:isDirectory:在此上下文中调用是多余的并且可能很危险.

对于您的需求并且在您的问题的有限范围内,它可能不会成为问题,但以下解决方案既简单又容易出现未来问题:

NSFileManager *fileManager= [NSFileManager defaultManager];
NSError *error = nil;
if(![fileManager createDirectoryAtPath:directory withIntermediateDirectories:YES attributes:nil error:&error]) {
     // An error has occurred, do something to handle it
     NSLog(@"Failed to create directory \"%@\". Error: %@", directory, error);
}
Run Code Online (Sandbox Code Playgroud)

另请注意Apple的文档:

回报价值

如果已创建目录,则为YES,如果设置了createIntermediates,则为YES,并且目录已存在),如果发生错误,则为NO.

因此,设置createIntermediatesYES您已经执行的操作是事实上检查目录是否已存在.