NSFileManager:如果存在重复文件

Posted

技术标签:

【中文标题】NSFileManager:如果存在重复文件【英文标题】:NSFileManager: duplicate file if exists 【发布时间】:2013-02-27 08:46:42 【问题描述】:

复制文件时,我希望在我的 ios 应用程序中使用 OSX 行为:如果存在,请在其上附加一个计数器:

myFile.png => myFile 1.png myFile20.png => myFile20 1.png 我的文件 20.png => 我的文件 21.png ...

是否有内置的方法可以做到这一点,还是我必须自己构建该功能?我找不到类似的东西,但我认为我不是第一个需要这种行为的人......

【问题讨论】:

你必须自己做。 【参考方案1】:

您可以这样做,其中requestedName 是用户选择的文件名,extension 是文件的扩展名,basePath 是您尝试将其存储到的文件夹:

 NSFileManager *fm = [NSFileManager defaultManager];
 NSString * filename = requestedName;

 if ([fm fileExistsAtPath:[basePath stringByAppendingPathComponent:requestedName]]) 
   
     unsigned int counter = 1;
     while ( [fm fileExistsAtPath: [basePath stringByAppendingPathComponent: filename]]) 
     
         //NSLog(@"File already exists %@", filename);
         NSURL *originalFilePath = [NSURL URLWithString:[kTempPath stringByAppendingPathComponent:filename]];
         filename = [[NSString stringWithFormat: @"%@-%d",
         [requestedName stringByDeletingPathExtension], counter]stringByAppendingPathExtension: extension];
         counter ++;
         NSURL *newFilePath = [NSURL URLWithString:[kTempPath stringByAppendingPathComponent:filename]];
         [fm moveItemAtURL:originalFilePath toURL:newFilePath error:nil]; 
      // just in case
         if (counter > 512) break;
     

如果文件不存在,则只需使用 NSFileManager 中的moveItemAtURLmoveItemAtPath将其移动到正确的位置。

【讨论】:

【参考方案2】:

您可以只更改源文件名,并将该名称用作源路径最后一个组件。 就像这样:

-(XMPFile*) duplicateDocument:(XMPFile*)file error:(NSError **)error

    NSString *filePath = [file path];
    NSString *destinationPath = [[file path] stringByDeletingLastPathComponent];
    NSString *pathExtension = [filePath pathExtension];

    NSFileManager *fileManager = [NSFileManager defaultManager];
    NSString *fileName = [[[file path] lastPathComponent] stringByDeletingPathExtension];

    unsigned int counter = 2;

    while ([fileManager fileExistsAtPath:filePath])
    
        NSString *duplicatedFilePathLastComponent = [[NSString stringWithFormat: @"%@ %d", fileName, counter] stringByAppendingPathExtension: pathExtension];

        NSString *duplicatedFilePath = [destinationPath stringByAppendingPathComponent:duplicatedFilePathLastComponent];

        if (![fileManager fileExistsAtPath:destinationPath]) 
            if ([fileManager copyItemAtPath:filePath toPath:duplicatedFilePath error:error]) 
                XMPFile *duplicatedXMPFile = [[XMPFile alloc] initWithPath:duplicatedFilePath];
                return duplicatedXMPFile;
            
        

        counter ++;
    
    return nil;

如果你愿意,你也可以添加错误信息

【讨论】:

【参考方案3】:

我认为 NSFileManager 中没有任何内置机制。您很可能需要通过检查错误类型来实现自己的。如果错误属于“已经存在”,则尝试附加适当的计数器并复制。

【讨论】:

【参考方案4】:

iOS 不支持。

您将需要生成随机计数器(可能是时间刻度)并将其附加到文件名。

【讨论】:

【参考方案5】:

我意识到这里已经有几个答案,但我觉得我的答案比提供的答案更直接。

我也需要解决这个问题。我刚刚定义了一个函数,以便可以轻松地对其进行单元测试。

- (NSString*)findNextValidFilePathAt:(NSString*)destination
                        withFileName:(NSString*)fileName

    NSFileManager* filemgr = [NSFileManager defaultManager];
    NSString* newFilePath = [destination stringByAppendingPathComponent:fileName];
    NSString* originalFilePathWithoutExtension = [newFilePath stringByDeletingPathExtension];
    NSString* pathExtension = [fileName pathExtension];
    int numberToAppend = 0;

    while ([filemgr fileExistsAtPath:newFilePath] && numberToAppend <= 99)
    
        // find a new file path to try: <original_path> <number>.<extension>
        // Ex: /users/alex/desktop/image 1.png
        numberToAppend++;
        newFilePath = [NSString stringWithFormat:@"%@ %d.%@",
                       originalFilePathWithoutExtension,
                       numberToAppend,
                       pathExtension];
    

    return newFilePath;

【讨论】:

以上是关于NSFileManager:如果存在重复文件的主要内容,如果未能解决你的问题,请参考以下文章

NSFileManager.contentsOfDirectoryAtURL 返回的文件根据 NSFileManager.fileExistsAtPath 不存在?

使用nsfilemanager设置文件夹的权限[重复]

文件存在路径:(NSFileManager)

NSFileManager 在文件夹中搜索图像文件

NSFileManager 说文件不可写 Mac

NSFileManager removeItemAtPath:error: 不尊重 POSIX 权限