- Фантастика и фэнтези
- Ироническое фэнтези
- Стимпанк
- Детективная фантастика
- Киберпанк
- Попаданцы
- LitRPG
- Космоопера
- Технофэнтези
- Городская фантастика
- Русское фэнтези
- Юмористическая фантастика
- Космическая фантастика
- Боевое фэнтези
- Эпическая фантастика
- Зарубежная фантастика
- Книги магов
- Мистика
- Разная фантастика
- Разное фэнтези
- Любовное фэнтези
- Романтическая фантастика
- Городское фентези
- Историческая фантастика
- Историческое фэнтези
- Социально-философская фантастика
- Сказочная фантастика
- Иностранное фэнтези
- Романтическое фэнтези
- Ироническая фантастика
- Ужасы и Мистика
- Постапокалипсис
- Героическая фантастика
- Фэнтези
- Научная Фантастика
- Социально-психологическая
- Альтернативная история
- Боевая фантастика
- Разная литература
- Пословицы, поговорки
- Шахматы
- Визуальные искусства
- Фанфик
- Авто и ПДД
- Военное
- Отраслевые издания
- Гиды, путеводители
- Зарубежная образовательная литература
- Военная история
- Цитаты из афоризмов
- Современная литература
- Великолепные истории
- Начинающие авторы
- Современная зарубежная литература
- Боевые искусства
- Изобразительное искусство, фотография
- Кино
- Литература 19 века
- Недвижимость
- Музыка, музыканты
- Готические новеллы
- Истории из жизни
- Культура и искусство
- Спецслужбы
- Зарубежная прикладная литература
- Музыка, танцы
- Подростковая литература
- Прочее
- Военная техника, оружие
- Газеты и журналы
- Периодические издания
- Домоводство, Дом и семья
- Любовные романы
- Экономическая литература
- Научные и научно-популярные книги
- О животных
- Биохимия
- Культурология
- Юриспруденция
- Политика
- Психотерапия
- Языкознание
- Научпоп
- Медицина
- Психология, личное
- Радиотехника
- Филология
- Педагогика
- Образовательная литература
- Деловая литература
- Физика
- Науки: разное
- Химия
- Воспитание детей, педагогика
- Детская психология
- Зарубежная публицистика
- Биология
- Архитектура
- Зарубежная психология
- Науки о космосе
- Социология
- Математика
- География
- Беременность, ожидание детей
- Литературоведение
- Транспорт, военная техника
- Обществознание
- Зоология
- География
- Альтернативная медицина
- Иностранные языки
- Ветеринария
- Рефераты
- Астрология
- Биофизика
- Экология
- История Европы
- Учебники
- Шпаргалки
- Государство и право
- Ботаника
- Религиоведение
- История
- Техническая литература
- Прочая научная литература
- Психология
- Детективы и Триллеры
- Справочная литература
- Проза
- Новелла
- Юмор
- Проза
- Историческая проза
- Русская современная проза
- Советская классическая проза
- Повести
- Очерки
- Эссе
- Рассказы
- Зарубежная современная проза
- Сентиментальная проза
- Зарубежная классика
- Афоризмы
- Эпистолярная проза
- Феерия
- Семейный роман/Семейная сага
- Разное
- Антисоветская литература
- Магический реализм
- Русская классическая проза
- Современная проза
- О войне
- Контркультура
- Классическая проза
- Поэзия, Драматургия
- Детская литература
- Детская фантастика
- Детские остросюжетные
- Детские стихи
- Детские приключения
- Внеклассное чтение
- Учебная литература
- Зарубежные детские книги
- Бизнес
- Загадки
- Книги для подростков
- Школьные учебники
- Детский фольклор
- Книги для дошкольников
- Детские детективы
- Детская познавательная и развивающая литература
- Буквари
- Прочая детская литература
- Сказка
- Детская проза
- Детская образовательная литература
- Юмор
- Документальные книги
- Бизнес
- Внешнеэкономическая деятельность
- Тайм-менеджмент
- Кадровый менеджмент
- О бизнесе популярно
- Управление, подбор персонала
- Бизнес
- Менеджмент и кадры
- Продажи
- Экономика
- Ценные бумаги и инвестиции
- Малый бизнес
- Делопроизводство, офис
- Корпоративная культура, бизнес
- Банковское дело
- Финансы
- Зарубежная деловая литература
- Ораторское искусство / риторика
- Личные финансы
- Интернет-бизнес
- Поиск работы
- Государственное и муниципальное управление
- Бухучет и аудит
- Работа с клиентами
- Менеджмент
- Краткое содержание
- Личная эффективность
- Переговоры
- Приключения
- Старинная литература
- Религия и духовность
- Компьютеры и Интернет
- Блог
Читаем без скачивания Освой самостоятельно за 21 день - Джесс Либерти
Шрифт:
Интервал:
Закладка:
Опробуйте эту программу с рядом значений для размера массива. Затем попытайтесь ввести значение -5. Вы могли бы ожидать, что будет вызвано исключение xNegative, но этому помешает порядок проверок, заданный в конструкторе: проверка size < 10 выполняется до проверки size < 1. Чтобы исправить этот недостаток, поменяйте строки 61 и 62 со строками 65 и 66 и перекомпилируйте программу.
Наследование исключений
Исключения — это классы, а раз так, то от них можно производить другие классы. Предположим, что нам нужно создать класс xSize и произвести от него классы xZero, xTooSmall, xTooBig и xNegative. В результате для одних функций можно установить перехват ошибки xSize, а для других — перехват типов ошибок, произведенных от xSize. Реализация этой идеи показана в листинге 20.3.
Листинг 20.3. Наследование исключений
1: #include <iostream.h>
2:
3: const int DefaultSize = 10;
4:
5: class Array
6: {
7: public:
8: // конструкторы
9: Array(int itsSize = DefaultSize);
10: Array(const Array &rhs);
11: ~Array() { delete [] pType;}
12:
13: // операторы
14: Array& operator=(const Array&);
15: int& operator[](int offSet);
16: const int& operator[](int offSet) const;
17:
18: // методы доступа
19: int GetitsSize() const { return itsSize; }
20:
21: // функция-друг
22: friend ostream& operator<< (ostream&, const Array&);
23:
24: // определения классов исключений
25: class xBoundary { };
26: class xSize { };
27: class xTooBig : public xSize { };
28: class xTooSmall : public xSize { };
29: class xZero : public xTooSmall { };
30: class xNegative : public xSize { };
31: private:
32: int *pType;
33: int itsSize;
34: };
35:
36:
37: Array::Array(int size):
38: itsSize(size)
39: {
40: if (size — 0)
41: throw xZero();
42: if (size > 30000)
43: throw xTooBig();
44: if (size <1)
45: throw xNegative();
46: if (size < 10)
47: throw xTooSmall();
48:
49: pType = new int[size];
50: for (int i = 0; i<size; i++)
51: pType[i] = 0;
52: }
53:
54: int& Array::operator[](int offSet)
55: {
56: int size = GetitsSize();
57: if (offSet >= 0 && offSet < GetitsSize())
58: return pType[offSet];
59: throw xBoundary();
60: return pType[0]; // требование компилятора
61: }
62:
63:
64: const int&Array::operator[](int offSet) const
65: {
66: int mysize = GetitsSize();
67: if (offSet >= 0 && offSet < GetitsSize())
68: return pType[offSet];
69: throw xBoundary();
70:
71: return pType[0]; // требование компилятора
72: }
73:
74: int main()
75: {
76:
77: try
78: {
79: Array intArray(0);
80: for (int j = 0; j< 100; j++)
81: {
82: intArray[j ] = j;
83: cout << "intArray[" << j << "] okay...n";
84: }
85: }
86: catch (Array::xBoundary)
87: {
88: cout << "Unable to process your input!n";
89: }
90: catch (Array::xTooBig)
91: {
92: cout << "This array is too big...n";
93: }
94:
95: catch (Array::xTooSmall)
96: {
97: cout << "This array is too small...n";
98: }
99: catch (Array::xZero)
100: {
101: cout << "You asked for an array";
102: cout << " of zero objects!n";
103: }
104:
105:
106: catch (.. .)
107: {
108: cout << "Something went wrong!n";
109: }
110: cout << "Done.n";
111: return 0;
112: }
Результат:
This array is too small...
Done.
Анализ: Здесь существенно изменены строки 27—30, где устанавливается иерархия классов. Классы xTooBig, xTooSmall и xNegative произведены от класса xSize, а класс xZero — от класса xTooSmall.
Класс Array создается с нулевым размером, но что это значит? Казалось бы, неправильное исключение будет тут же перехвачено! Однако тщательно исследуйте блок catch, и вы поймете, что, прежде чем искать исключение типа xZero, в нем ищется исключение типа xTooSmall. А поскольку возник объект класса xZero, который также является объектом класса xTooSmall, то он перехватывается обработчиком исключения xTooSmall. Будучи уже обработанным, это исключение не передается другим обработчикам, так что обработчик исключений типа xZero никогда не вызывается.
Решение этой проблемы лежит в тщательном упорядочении обработчиков таким образом, чтобы самые специфические из них стояли в начале, а более общие следовали за ними. В данном примере для решения проблемы достаточно поменять местами два обработчика — xZero и xTooSmall.
Данные в классах исключений и присвоение имен объектам исключений
Часто для того, чтобы программа могла отреагировать должным образом на ошибку, полезно знать несколько больше, чем просто тип возникшего исключения. Классы исключений — это такие же классы, как и любые другие. Вы абсолютно свободно можете добавлять любые данные в эти классы, инициализировать их с помощью конструктора и считывать их значения в любое время, как показано в листинге 20.4.
Листинг 20.4. возвращение данных из объекта исключения
1: #include <iostream.h>
2:
3: const int DefaultSize = 10;
4:
5: class Array
6: {
7: public:
8: // конструкторы
9: Array(int itsSize = DefaultSize);
10: Array(const Array &rhs);
11: ~Array() { delete [] pType;}
12:
13: // операторы
14: Array& operator=(const Array&);
15: int& operator[](int offSet);
16: const int& operator[](int offSet) const;
17:
18: // методы доступа
19: int GetitsSize() const { return itsSize; }
20:
21: // функция-друг
22: friend ostream& operator<< (ostream&, const Array&);
23:
24: // определение классов исключений
25: class xBoundary { };
26: class xSize
27: {
28: public:
29: xSize(int size):itsSize(size) { }
30: ~xSize(){ }
31: int GetSize() { return itsSize; }
32: private:
33: int itsSize;
34: };
35:
36: class xTooBig : public xSize
37: {
38: public:
39: xTooBig(int size):xSize(size){ }
40: };
41:
42: class xTooSmall : public xSize
43: {
44: public:
45: xTooSmall(int size):xSize(size){ }
46: };
47:
48: class xZero : public xTooSmall
49: {
50: public:
51: xZero(int size):xTooSmall(size){ }
52: };
53:
54: class xNegative : public xSize
55: {
56: public:
57: xNegative(int size):xSize(size){ }
58: };
59:
60: private:
61: int *pType;
62: int itsSize;
63: };
64:
65:
66: Array::Array(int size):
67: itsSize(size)
68: {
69: if (size == 0)
70: throw xZero(size);
71: if (size > 30000)
72: throw xTooBig(size);
73: if (size <1)
74: throw xNegative(size);
75: if (size < 10)
76: throw xTooSnall(size);
77:
78: pType = new int[size];
79: for (int i = 0; i<size; i++)
80: pType[i] = 0;
81: }
82:
83:
84: int& Array::operator[] (int offSet)
85: {
86: int size = GetitsSize();
87: if (offSet >= 0 && offSet < GetitsSize())
88: return pType[offSet];
89: throw xBoundary();
90: return pType[0];
91: }
92:
93: const int&Array::operator[] (int offSet) const
94: {
95: int size = GetitsSize();
96: if (offSet >= 0 && offSet < GetitsSize())
97: return pType[offSet];
98: throw xBoundary();
99: return pType[0];
100: }
101:
102: int main()
103: {
104:
105: try
106: {
107: Array intArray(9);
108: for (int j = 0; j< 100; j++)
109: {
110: intArray[j] = j;
111: cout << "intArray[" << j << "] okay..." << endl;
112: }
113: }
114: catch (Array::xBoundary)
115: {
116: cout << "Unable to process your input!n";
117: }
118: catch(Array::xZero theException)
119: {
120: cout << "You asked for an Array of zero objectsl " << endl;
121: cout << "Received " << theExesptiQn,GatSize() << endl;
122: }
123: catch (Array:;xTooBig theException)
124: {
125: cout << "This Array is too big,,, " << endl;
126: cout << "Received " << theException,GetSize() << endl;
127: }
128: catch (Array;:xTooSmall theException)
129: {
130: cout << "This Array is too small... " << endl;
131: cout << "Received " << theException.GetSize() << endl;
132: }
133: catch (...)
134: {
135: cout << "Something went wrong, but I've no idea what!n";
136: }
137: cout << "Done.n";
138: return 0;
139: }
Результат:
This array is too small...
Received 9
Done.
Анализ: Объявление класса xSize было изменено таким образом, чтобы включить в него переменную-член itsSize (строкаЗЗ) и функцию-член GetSize() (строка 31). Кроме того, был добавлен конструктор, который принимает целое число и инициализирует переменную-член, как показано в строке 29.