Чтение онлайн

на главную - закладки

Жанры

Программирование на Objective-C 2.0
Шрифт:

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

Рассмотрим программу 9.4. В определении класса Fraction у нас не было метода с именем noSuchMethod («нет такого метода»). При компиляции этой программы вы получите из-за этого предупреждающие сообщения. #import Traction.h" int main (int arge, char *argv []) { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; Fraction *f = [[Fraction alloc] init]; [f noSuchMethod]; NSLog (@"Execution continues!'’); [f release]; [pool drain]; return 0; }

Несмотря на эти предупреждающие сообщения, вы можете попытаться продолжить работу и выполнить программу. В этом случае программа будет аварийно завершена с выводом следующих сообщений об ошибках. Вывод программы 9.4 -[Fraction noSuchMethod]: unrecognized selector sent to instance 0x103280 (... нераспознанный селектор передан экземпляру) *** Terminating арр due to uncaught exception ’NSInvalidArgumentException', (Прекращение работы приложения из-за необработанного исключения) reason: ’*** -[Fraction noSuchMethod]: unrecognized selector sent to instance 0x103280’ (причина: ... нераспознанный селектор передан экземпляру) Stack: ( 2482717003, 2498756859, 2482746186, 2482739532, 2482739730 ) Trace/BPT trap

Чтобы избежать аварийного завершения программы, можно поместить оди н или несколько операторов в блоке операторов, имеющем следующий формат. @try { оператор оператор } @catch (NSException *exception) { оператор оператор )

Выполнение программы в блоке @try происходит как обычно. Однако если один из операторов в этом блоке выдает исключение, работа программы нс прекращается, а управление передастся в блок @catch, где продолжается ее выполнение. Внутри этого блока можно обрабатывать исключение. Последовательностью действий в этом случае может быть вывод сообщения об ошибке, очистка и завершение работы программы.

В профамме 9.5 показана обработка исключения. Затем приводится вывод программы. #import "Fraction.h" int main {int arge, char *argv []) { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; Fraction *f = [[Fraction alloc] init]; @try { [f noSuchMethod]; } @catch (NSException *exception) { NSLog(@"Caught %@%@", [exception name], [exception reason]); } NSLog (@"Execution continues!"); [f release]; [pool drain]; return 0; }

Вывод программы 9.5 *** -[Fraction noSuchMethod]: unrecognized selector sent to instance 0x103280 Caught NSInvalidArgumentException: *** -[Fraction noSuchMethod]: unrecognized selector sent to instance 0x103280 Execution continues! (Выполнение продолжается!)

Если возникает исключительная ситуация, выполняется блок @catch. Объект NSExceptton, который содержит информацию об исключении, передастся в этот блок как аргумент. Мметод name считывает имя исключения, а метод reason указывает причину (которую система runtime раньше выводила автоматически). После выполнения последнего оператора в блоке @catch (здесь только один оператор) программа продолжает выполнение, начиная с оператора, который непосредственно следует за этим блоком. В данном случае мы выполняем вызов NSLog, чтобы подтвердить, что выполнение не было прекращено.

Это очень простой пример, показывающий, как перехватывать исключения в профамме. Можно также использовать блок @finally, чтобы включить код, выполняемый независимо от возникновения исключительной ситуации в каком- либо операторе блока @try.

Директива @throw позволяет создавать ваше собственное исключение. Ее можно использовать для создания конкретного исключения или внугри блока @catch для создания той же исключительной ситуации, которая вызвала переход в этот блок: @throw;

Это может потребоваться после вашей собственной обработки исключения (например, после выполнения операций очистки). После этого вы можете передать системе остальную часть работы. И, наконец, у вас может быть несколько блоков @catch, которые следуют в определенном порядке для перехвата и обработки исключений различного типа. Упражнения

Что произойдет, если вставить выражение с сообщением [compResult reduce]; в профамму 9.1 после того, как выполнено сложение (но до выполнения release для compResult)? Попробуйте и посмотрите, что получится.

Можно ли переменной dataValue типа id (определенной в профамме 9.2) присвоить объект класса Rectangle в соответствии с его определением в главе 8? Иначе говоря, является ли допустимым оператор dataValue = [[Rectangle alloc] init]; Почему?

Добавьте метод print к классу XYPoint, определенному в главе 8. Он должен выводить точку в формате (х,у). Затем внесите изменения в программу 9.2, чтобы включить объект типа XYPoint. Эта модифицированная программа должна создавать объект типа XYPoint, задавать его значение, присваивать его переменной dataValue типа id и затем выводить его значение.

Вспомните, что говорилось в этой главе о типах ар1ументов и возвращаемых значений, и модифицируйте методы add: в классах Fraction и Complex, чтобы принимать и возвращать объекты типа id. Затем напишите программу, которая включает следующую последовательность кода. result = [dataValuel add: dataValue2]; [result print];

Здесь result, dataValuel и dataValue2 — это объекты типа id. He забудьте задать образом значения dataValuel и dataValue2 в программе и освободить (release) все объекты, прежде чем завершить программу.

Примечание. Вам придется изменить имна этих методов. Системный класс NSObjectController тоже содержит метод add:. Как говорилось выше в разделе «Типы аргументов и возвращаемых значений при динамическом контроле типов», в случае существования нескольких методов с одним именем в разных классах, если на этапе компиляции тип получателя неизвестен, компилятор выполняет проверку согласованности типов аргументов и возвращаемого значения с методами, имеющими одинаковые имена.

Используя определения классов Fraction и Complex, заданные в этой книге, и определения Fraction *fraction = [[Fraction alloc] init]; Complex *complex = [[Complex alloc] init]; id number = [[Complex alloc] init]; определите возвращаемое значение для следующих выражений с сообщениями. Затем введите их в программу, чтобы проверить результаты. [fraction isMemberOfClass: [Complex class]]; [complex isMemberOfClass: [NSObject class]]; [complex isKindOfClass: [NSObject class]]; [fraction isKindOfClass: [Fraction class]]; [fraction respondsToSelector: @selector (print)]; [complex respondsToSelector: @selector (print)]; [Fraction instancesRespondToSelector: @selector (print)]; [number respondsToSelector: @selector (print)]; [number isKindOfClass: [Complex class]]; [number respondsToSelector: @selector (release)]; [[number class] respondsToSelector: @selector (alloc)];

Глава 10. Более подробно о переменных и типах данных

В этой главе мы поговорим об области действия переменных, методах инициализации для объектов и типах данных. В главе 7 мы кратко обсуждали область действия переменных экземпляра, статические и локальные переменные. Теперь мы более подробно поговорим о статических переменных и введем понятие глобальных и внешних переменных. Для компилятора Objective-C можно задавать директивы, позволяющие контролировать область действия переменных экземпляра. В этой главе мы рассмотрим их.

Поделиться:
Популярные книги

Личный аптекарь императора. Том 5

Карелин Сергей Витальевич
5. Личный аптекарь императора
Фантастика:
городское фэнтези
попаданцы
аниме
сказочная фантастика
фэнтези
7.50
рейтинг книги
Личный аптекарь императора. Том 5

Кодекс Охотника. Книга II

Винокуров Юрий
2. Кодекс Охотника
Фантастика:
фэнтези
попаданцы
боевая фантастика
юмористическое фэнтези
5.00
рейтинг книги
Кодекс Охотника. Книга II

Студент из прошлого тысячелетия

Еслер Андрей
2. Соприкосновение миров
Фантастика:
героическая фантастика
попаданцы
аниме
5.00
рейтинг книги
Студент из прошлого тысячелетия

Последний Герой. Том 5

Дамиров Рафаэль
5. Последний герой
Фантастика:
попаданцы
альтернативная история
5.00
рейтинг книги
Последний Герой. Том 5

На границе империй. Том 8

INDIGO
12. Фортуна дама переменчивая
Фантастика:
космическая фантастика
попаданцы
5.00
рейтинг книги
На границе империй. Том 8

Адвокат Империи 14

Карелин Сергей Витальевич
14. Адвокат империи
Фантастика:
городское фэнтези
аниме
попаданцы
5.00
рейтинг книги
Адвокат Империи 14

Ваше Сиятельство 4т

Моури Эрли
4. Ваше Сиятельство
Любовные романы:
эро литература
5.00
рейтинг книги
Ваше Сиятельство 4т

Кодекс Охотника

Винокуров Юрий
1. Кодекс Охотника
Фантастика:
фэнтези
юмористическое фэнтези
попаданцы
боевая фантастика
5.00
рейтинг книги
Кодекс Охотника

Алые перья стрел

Крапивин Владислав Петрович
Детские:
детские приключения
8.58
рейтинг книги
Алые перья стрел

Кодекс Крови. Книга VII

Борзых М.
7. РОС: Кодекс Крови
Фантастика:
боевая фантастика
попаданцы
аниме
5.00
рейтинг книги
Кодекс Крови. Книга VII

Черный Маг Императора 14

Герда Александр
14. Черный маг императора
Фантастика:
аниме
сказочная фантастика
фэнтези
фантастика: прочее
попаданцы
5.00
рейтинг книги
Черный Маг Императора 14

Древесный маг Орловского княжества 3

Павлов Игорь Васильевич
3. Орловское княжество
Фантастика:
аниме
сказочная фантастика
фэнтези
попаданцы
гаремник
5.00
рейтинг книги
Древесный маг Орловского княжества 3

Снайпер

Поселягин Владимир Геннадьевич
3. Жнец
Фантастика:
боевая фантастика
попаданцы
5.60
рейтинг книги
Снайпер

Элизиум. Аликс и монеты

Андерсон Александр
1. Элизиум
Фантастика:
фэнтези
сказочная фантастика
8.98
рейтинг книги
Элизиум. Аликс и монеты