NSFileManager - Копирование файлов при запуске - PullRequest
4 голосов
/ 15 мая 2010

Мне нужно скопировать несколько примеров файлов из папки ресурсов моего приложения и поместить их в папку документов моего приложения. Я придумал прикрепленный код, он прекрасно компилируется, но не работает. Все каталоги, на которые я ссылаюсь, существуют. Я не совсем уверен, что я делаю неправильно, кто-то может указать мне правильное направление, пожалуйста?

NSFileManager*manager = [NSFileManager defaultManager];

NSString*dirToCopyTo = [NSHomeDirectory() stringByAppendingPathComponent:@"Documents"];

NSString*path = [[NSBundle mainBundle] resourcePath];

NSString*dirToCopyFrom = [path stringByAppendingPathComponent:@"Samples"];


NSError*error;

NSArray*files = [manager contentsOfDirectoryAtPath:dirToCopyFrom error:nil];

for (NSString *file in files)
{
        [manager copyItemAtPath:[dirToCopyFrom stringByAppendingPathComponent:file] toPath:dirToCopyTo error:&error];

        if (error)
        {
            NSLog(@"%@",[error localizedDescription]);
    }
}

РЕДАКТИРОВАТЬ: я просто отредактировал код так, как он должен быть. Однако теперь есть еще одна проблема:

2010-05-15 13: 31: 31.787 WriteIt Мобильный [4587: 207] DAMutableDictionary.h 2010-05-15 13: 31: 31.795 WriteIt Мобильный [4587: 207] FileManager Ошибка: операция не может быть завершено. Файл существует

РЕДАКТИРОВАТЬ: я исправил проблему, сообщив NSFileManager имена адресатов скопированных файлов.

        [manager copyItemAtPath:[dirToCopyFrom stringByAppendingPathComponent:file] toPath:[dirToCopyTo stringByAppendingPathComponent:file] error:&error];

Ответы [ 4 ]

5 голосов
/ 15 мая 2010

Я думаю, что проблема в этой строке:

NSArray*files = [manager contentsOfDirectoryAtPath:dirToCopyTo error:nil];

Вы перечисляете файлы в каталоге назначения вместо источника. Измените его на что-то вроде:

NSArray*files = [manager contentsOfDirectoryAtPath:dirToCopyFrom error:nil];

И с тобой все будет в порядке.

2 голосов
/ 04 сентября 2011

Обратите внимание, что длительная операция при запуске должна быть исключена:

  1. Плохой пользовательский опыт (задержка и плохое поведение)
  2. Watchdog в iOS может убить ваше приложение, как будто оно застряло.

Выполните копирование во вторичном потоке (или в операции ... или в другом месте, где используется другой путь выполнения).

Другая проблема возникнет, если вам понадобятся данные для заполнения вашего пользовательского интерфейса: в этом случае:

  • Отключить элементы пользовательского интерфейса
  • Запустить асинхронную / потоковую операцию
  • При завершении обратного вызова копирования (через уведомление, протокол ... или иным способом) уведомить интерфейс пользовательского интерфейса, что он может начать выборку данных.

Например, мы копируем ZIP-файл и распаковываем его, но это занимает некоторое время, поэтому нам пришлось поместить его в процедуру таймера, которая будет запускать пользовательский интерфейс по завершении.

Если вам нужен пример, дайте мне знать.

PS:
Копирование с использованием ZIP-файла более эффективно, как:

  1. Только вызов файловой системы
  2. Гораздо меньше байтов для копирования

Плохая новость: вы должны использовать процедуру распаковки zip-файла, но вы можете найти их в Интернете.

Распаковка Zip-файлов должна быть более эффективной, поскольку эти вызовы пишутся на прямом C, а не в Какао со всеми накладными расходами.

2 голосов
/ 15 мая 2010

Я думаю, что проблема в том, что вы читаете файлы для копирования из dirToCopyTo, и я думаю, что вы имели в виду dirToCopyFrom

Также, чтобы получить каталог документов, вы должны использовать NSDocumentDirectory с - (NSArray *) URLsForDirectory: (NSSearchPathDirectory) каталог inDomains: (NSSearchPathDomainMask) domainMask

1 голос
/ 15 мая 2010
    [manager copyItemAtPath:[dirToCopyFrom stringByAppendingPathComponent:file] toPath:dirToCopyTo error:&error];

Путь назначения - это путь, по которому вы хотите получить копию, , включая его имя файла. Вы не можете передать путь к каталогу, ожидающему, что NSFileManager заполнит имя исходного файла; это не сделает этого.

В документации говорится, что путь назначения не должен описывать ничего существующего:

… dstPath не должен существовать до операции.

В вашем случае это путь к каталогу назначения, поэтому он существует , поэтому копирование не удается.

Вам необходимо указать путь к файлу назначения, добавив к нему желаемое имя файла. Тогда он не будет существовать (если не был скопирован ранее), поэтому копирование будет выполнено успешно.

...