2009-10-11 3 views
2

Каков предпочтительный подход для постоянного обмена данными по потокам при использовании Core Data? Я загружаю большой файл и хочу показать ход загрузки в UIProgressBar. Фактическая загрузка происходит в фоновом потоке, созданном NSOperation.Основные данные, загрузки файлов и безопасность потоков

Информация о загрузке (локальный путь, общие байты, полученные байты) смоделирована как объект, управляемый основными данными, и фактический файл хранится в каталоге Documents /. Одним из решений, которые пришли мне на ум, было создание отдельного контекста управляемого объекта в фоновом потоке и передать его objectID и потянуть его, используя метод objectWithID:. Всякий раз, когда фоновый поток выполняет сохранение, основной поток получает уведомление, а основной контекст объединяет эти изменения, и табличное представление впоследствии обновляется.

Этот подход работает, но сохранение не может быть выполнено слишком часто или пользовательский интерфейс замерзает. Таким образом, пользовательский интерфейс обновляется после получения каждого X Кбайта данных, где X должен быть не менее 500 КБ для того, чтобы пользовательский интерфейс был несколько отзывчивым. Есть ли лучший способ передать данные о ходе загрузки в основной поток по мере его получения?

EDIT: Использует ли KVO любую помощь? Если да, знаете ли вы о каких-либо хороших учебниках по этой теме?

ответ

4

Я знаю, что вы уже создали свою собственную систему, но я использую ASIHTTPRequest для всех своих сетевых операций. Он очень надежный и имеет массу полезных свойств, таких как возобновление файлов, сохранение непосредственно на диск, мониторинг выполнения загрузки, мониторинг отслеживания хода и кухонная раковина. Если вы его не используете, вы можете посмотреть источник, чтобы узнать, как они это делают, потому что пользовательский интерфейс никогда не зависает, когда я использую отчет о ходе работы в этой структуре.

+0

Во-первых, это здорово, что можно повысить! ASIHTTPRequest выглядит очень красиво, и я буду интегрировать его в свой код. Он предлагает гораздо больше функциональности, чем моя небольшая загрузочная среда, и это с открытым исходным кодом :) – Anurag

0

Хотя я собираюсь использовать ASIHTTPRequest для своего проекта, все равно хорошо упомянуть о моем решении проблемы для полноты. Это очевидно, но сохранение основного информационного контекста так часто, как каждые пару секунд - ужасная ошибка.

Вместо этого я добавил делегата прогресса в операцию загрузки, которая получает уведомление об обновлении в основном потоке.

NSNumber bytesDownloaded = [NSNumber numberWithLongLong:[data length]]; 
[downloadDelegate performSelectorOnMainThread:@selector(updateProgress:) withObject:bytesDownloaded waitUntilDone:NO]; 

Важно, чтобы информация о ходе выполнения передачи передавалась делегату в основном потоке. Делегат обновляет ход выполнения, сохраняет накопленные изменения и сохраняет его при завершении загрузки или с гораздо большими интервалами.

Смежные вопросы