- Фантастика и фэнтези
- Ироническое фэнтези
- Стимпанк
- Детективная фантастика
- Киберпанк
- Попаданцы
- LitRPG
- Космоопера
- Технофэнтези
- Городская фантастика
- Русское фэнтези
- Юмористическая фантастика
- Космическая фантастика
- Боевое фэнтези
- Эпическая фантастика
- Зарубежная фантастика
- Книги магов
- Мистика
- Разная фантастика
- Разное фэнтези
- Любовное фэнтези
- Романтическая фантастика
- Городское фентези
- Историческая фантастика
- Историческое фэнтези
- Социально-философская фантастика
- Сказочная фантастика
- Иностранное фэнтези
- Романтическое фэнтези
- Ироническая фантастика
- Ужасы и Мистика
- Постапокалипсис
- Героическая фантастика
- Фэнтези
- Научная Фантастика
- Социально-психологическая
- Альтернативная история
- Боевая фантастика
- Разная литература
- Пословицы, поговорки
- Шахматы
- Визуальные искусства
- Фанфик
- Авто и ПДД
- Военное
- Отраслевые издания
- Гиды, путеводители
- Зарубежная образовательная литература
- Военная история
- Цитаты из афоризмов
- Современная литература
- Великолепные истории
- Начинающие авторы
- Современная зарубежная литература
- Боевые искусства
- Изобразительное искусство, фотография
- Кино
- Литература 19 века
- Недвижимость
- Музыка, музыканты
- Готические новеллы
- Истории из жизни
- Культура и искусство
- Спецслужбы
- Зарубежная прикладная литература
- Музыка, танцы
- Подростковая литература
- Прочее
- Военная техника, оружие
- Газеты и журналы
- Периодические издания
- Домоводство, Дом и семья
- Любовные романы
- Экономическая литература
- Научные и научно-популярные книги
- О животных
- Биохимия
- Культурология
- Юриспруденция
- Политика
- Психотерапия
- Языкознание
- Научпоп
- Медицина
- Психология, личное
- Радиотехника
- Филология
- Педагогика
- Образовательная литература
- Деловая литература
- Физика
- Науки: разное
- Химия
- Воспитание детей, педагогика
- Детская психология
- Зарубежная публицистика
- Биология
- Архитектура
- Зарубежная психология
- Науки о космосе
- Социология
- Математика
- География
- Беременность, ожидание детей
- Литературоведение
- Транспорт, военная техника
- Обществознание
- Зоология
- География
- Альтернативная медицина
- Иностранные языки
- Ветеринария
- Рефераты
- Астрология
- Биофизика
- Экология
- История Европы
- Учебники
- Шпаргалки
- Государство и право
- Ботаника
- Религиоведение
- История
- Техническая литература
- Прочая научная литература
- Психология
- Детективы и Триллеры
- Справочная литература
- Проза
- Новелла
- Юмор
- Проза
- Историческая проза
- Русская современная проза
- Советская классическая проза
- Повести
- Очерки
- Эссе
- Рассказы
- Зарубежная современная проза
- Сентиментальная проза
- Зарубежная классика
- Афоризмы
- Эпистолярная проза
- Феерия
- Семейный роман/Семейная сага
- Разное
- Антисоветская литература
- Магический реализм
- Русская классическая проза
- Современная проза
- О войне
- Контркультура
- Классическая проза
- Поэзия, Драматургия
- Детская литература
- Детская фантастика
- Детские остросюжетные
- Детские стихи
- Детские приключения
- Внеклассное чтение
- Учебная литература
- Зарубежные детские книги
- Бизнес
- Загадки
- Книги для подростков
- Школьные учебники
- Детский фольклор
- Книги для дошкольников
- Детские детективы
- Детская познавательная и развивающая литература
- Буквари
- Прочая детская литература
- Сказка
- Детская проза
- Детская образовательная литература
- Юмор
- Документальные книги
- Бизнес
- Внешнеэкономическая деятельность
- Тайм-менеджмент
- Кадровый менеджмент
- О бизнесе популярно
- Управление, подбор персонала
- Бизнес
- Менеджмент и кадры
- Продажи
- Экономика
- Ценные бумаги и инвестиции
- Малый бизнес
- Делопроизводство, офис
- Корпоративная культура, бизнес
- Банковское дело
- Финансы
- Зарубежная деловая литература
- Ораторское искусство / риторика
- Личные финансы
- Интернет-бизнес
- Поиск работы
- Государственное и муниципальное управление
- Бухучет и аудит
- Работа с клиентами
- Менеджмент
- Краткое содержание
- Личная эффективность
- Переговоры
- Приключения
- Старинная литература
- Религия и духовность
- Компьютеры и Интернет
- Блог
Читаем без скачивания iOS. Приемы программирования - Вандад Нахавандипур
Шрифт:
Интервал:
Закладка:
Итак, довольно теории, перейдем к примерам. В данном примере попытаемся собрать HTML-контент с домашней страницы Apple, а потом выведем эту информацию в строковом формате в окне консоли:
NSString *urlAsString = @"http://www.apple.com";
NSURL *url = [NSURL URLWithString: urlAsString];
NSURLRequest *urlRequest = [NSURLRequest requestWithURL: url];
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[NSURLConnection
sendAsynchronousRequest: urlRequest
queue: queue
completionHandler: ^(NSURLResponse *response,
NSData *data,
NSError *error) {
if ([data length] >0 &&
error == nil){
NSString *html = [[NSString alloc] initWithData: data
encoding: NSUTF8StringEncoding];
NSLog(@"HTML = %@", html);
}
else if ([data length] == 0 &&
error == nil){
NSLog(@"Nothing was downloaded.");
}
else if (error!= nil){
NSLog(@"Error happened = %@", error);
}
}];
Да, все так просто. Если вы хотите сохранить данные, которые мы загрузили на диск в ходе соединения, это можно сделать с помощью подходящих методов класса NSData, получаемых от завершающего блока:
NSString *urlAsString = @"http://www.apple.com";
NSURL *url = [NSURL URLWithString: urlAsString];
NSURLRequest *urlRequest = [NSURLRequest requestWithURL: url];
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[NSURLConnection
sendAsynchronousRequest: urlRequest
queue: queue
completionHandler: ^(NSURLResponse *response,
NSData *data,
NSError *error) {
if ([data length] >0 &&
error == nil){
/* Прикрепляем имя файла к каталогу с документами. */
NSURL *filePath =
[[self documentsFolderUrl]
URLByAppendingPathComponent:@"apple.html"];
[data writeToURL: filePath atomically: YES];
NSLog(@"Successfully saved the file to %@", filePath);
}
else if ([data length] == 0 &&
error == nil){
NSLog(@"Nothing was downloaded.");
}
else if (error!= nil){
NSLog(@"Error happened = %@", error);
}
}];
Все действительно просто. В более ранних версиях iOS SDK соединения по URL происходили с применением делегирования, но теперь модель стала обычной блоковой и вам не придется заниматься реализацией делегатов.
11.2. Обработка задержек при асинхронных соединениях
Необходимо задать лимит ожидания — проще говоря, задержку — при асинхронном соединении.
Решение
Задайте задержку в URL-запросе, посылаемом классу NSURLConnection.
Обсуждение
При инстанцировании объекта типа NSURLRequest для передачи URL-соединения можно воспользоваться методом класса requestWithURL: cachePolicy: timeoutInterval:, относящимся к этому объекту, и передать желаемую длительность задержки в секундах в параметре timeoutInterval.
Например, если вы готовы не более 30 секунд дожидаться, пока загрузится содержимое главной страницы Apple (с применением синхронного соединения), создайте ваш URL таким образом:
— (BOOL) application:(UIApplication *)application
didFinishLaunchingWithOptions:(NSDictionary *)launchOptions{
NSString *urlAsString = @"http://www.apple.com";
NSURL *url = [NSURL URLWithString: urlAsString];
NSURLRequest *urlRequest =
[NSURLRequest
requestWithURL: url
cachePolicy: NSURLRequestReloadIgnoringLocalAndRemoteCacheData
timeoutInterval:30.0f];
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[NSURLConnection
sendAsynchronousRequest: urlRequest
queue: queue
completionHandler: ^(NSURLResponse *response,
NSData *data,
NSError *error) {
if ([data length] >0 &&
error == nil){
NSString *html = [[NSString alloc] initWithData: data
encoding: NSUTF8StringEncoding];
NSLog(@"HTML = %@", html);
}
else if ([data length] == 0 &&
error == nil){
NSLog(@"Nothing was downloaded.");
}
else if (error!= nil){
NSLog(@"Error happened = %@", error);
}
}];
self.window = [[UIWindow alloc]
initWithFrame: [[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
return YES;
}
Что же здесь происходит? Дело в том, что среда времени исполнения пытается получить содержимое, расположенное по предоставленной ссылке. Если это удается сделать в течение заданных 30 секунд и соединение устанавливается до возникновения задержки — хорошо. В противном случае среда времени исполнения выдаст вам ошибку задержки (error) в соответствующем параметре завершающего блока.
11.3. Синхронная загрузка с применением NSURLConnection
Постановка задачи
Необходимо синхронно загрузить информацию, расположенную по имеющемуся URL.
Решение
Используйте метод класса sendSynchronousRequest: returningResponse: error:, относящийся к классу NSURLConnection. Возвращаемое значение этого метода — данные типа NSData.
Обсуждение
Пользуясь методом класса sendSynchronousRequest: returningResponse: error:, относящимся к классу NSURLConnection, можно посылать синхронный запрос к URL. А теперь внимание! Синхронные соединения не обязательно блокируют главный поток. Эти соединения блокируют актуальный поток, то есть выполняющий текущую задачу, и если этот поток не главный, то главный поток останется свободным. Если приступить к обработке глобальной параллельной очереди в GCD, а потом инициировать синхронное соединение, то вы не заблокируете главный поток.
Попробуем инициировать наше первое синхронное соединение и посмотрим, что произойдет. В данном примере мы попытаемся получить домашнюю страницу сайта Yahoo!:
— (BOOL) application:(UIApplication *)application
didFinishLaunchingWithOptions:(NSDictionary *)launchOptions{
NSLog(@"We are here…");
NSString *urlAsString = @"http://www.yahoo.com";
NSURL *url = [NSURL URLWithString: urlAsString];
NSURLRequest *urlRequest = [NSURLRequest requestWithURL: url];
NSURLResponse *response = nil;
NSError *error = nil;
NSLog(@"Firing synchronous url connection…");
NSData *data = [NSURLConnection sendSynchronousRequest: urlRequest
returningResponse:&response
error:&error];
if ([data length] > 0 &&
error == nil){
NSLog(@"%lu bytes of data was returned.", (unsigned long)[data length]);
}
else if ([data length] == 0 &&
error == nil){
NSLog(@"No data was returned.");
}
else if (error!= nil){
NSLog(@"Error happened = %@", error);
}
NSLog(@"We are done.");
self.window = [[UIWindow alloc] initWithFrame:
[[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
return YES;
}
Если запустить это приложение, а потом взглянуть в окно консоли, то там окажется выведен следующий результат:
We are here…
Firing synchronous url connection…
2 52117 bytes of data was returned.
We are done.
Итак, вполне очевидно, что актуальный поток написал на консоли строку We are here…, дождался окончания соединения (поскольку это синхронное соединение, блокирующее актуальный поток), а потом вывел в окне консоли текст We are done. Теперь проведем эксперимент. Поместим то же самое синхронное соединение в глобальной параллельной очереди в GCD, то есть гарантированно обеспечим параллелизм, и посмотрим, что произойдет:
— (BOOL) application:(UIApplication *)application
didFinishLaunchingWithOptions:(NSDictionary *)launchOptions{
NSLog(@"We are here…");
NSString *urlAsString = @"http://www.yahoo.com";
NSLog(@"Firing synchronous url connection…");
dispatch_queue_t dispatchQueue =
dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_async(dispatchQueue, ^(void) {
NSURL *url = [NSURL URLWithString: urlAsString];
NSURLRequest *urlRequest = [NSURLRequest requestWithURL: url];
NSURLResponse *response = nil;
NSError *error = nil;
NSData *data = [NSURLConnection sendSynchronousRequest: urlRequest
returningResponse:&response
error:&error];
if ([data length] > 0 &&
error == nil){
NSLog(@"%lu bytes of data was returned.", (unsigned long)[data length]);
}
else if ([data length] == 0 &&
error == nil){
NSLog(@"No data was returned.");
}
else if (error!= nil){
NSLog(@"Error happened = %@", error);
}
});
NSLog(@"We are done.");
self.window = [[UIWindow alloc] initWithFrame:
[[UIScreen mainScreen] bounds]];