
- •Глава 10, описывающая классы как контейнеры их статических членов,
- •Глава 13 посвящена отношениям между классами (и их объектами). Особое
- •Глава 18 включена в книгу при подготовке второго издания. Она посвящен
- •Глава 1. Объектная ориентация программ
- •1.1. Типы, классы, объекты
- •1.2. Программа на c#
- •1.3. Пространство имен
- •1.4. Создание консольного приложения
- •Глава 2. Типы в языке c#
- •2.1. Типы ссылок и типы значений
- •2.2. Классификация типов c#
- •2.3. Простые типы. Константы-литерал
- •2.4. Объявления переменных и констант базовых типо
- •If implicit in int interface
- •Internal is lock long namespace
- •Volatile while
- •Глава 3. Операции и целочисленные выражения
- •3.1. Операции языка c#
- •3.2. Операции присваивания и оператор
- •3.4. Выражения с арифметическими операциями
- •3.6. Переполнения при операциях с целыми
- •Глава 4. Выражения с операндами базовых
- •4.1. Автоматическое и явное приведение арифметических типов
- •4.2. Особые ситуации в арифметических выражениях
- •4.3. Логический тип и логические выражения
- •4.4. Выражения с символьными операндами
- •4.5. Тернарная (условная) операция
- •Глава 5. Типы с# как классы платформы .Net
- •5.1. Платформа .Net Framework и спецификация cts
- •5.2. Простые (базовые) типы c# как классы
- •5.3. Специфические методы и поля простых типов
- •Глава 6. Операторы
- •6.1. Общие сведения об операторах
- •6.2. Метки и оператор безусловного перехода
- •6.3. Условный оператор (ветвлений)
- •If (логическое выражение) оператор_1
- •6.4. Операторы цикла
- •6.5. Операторы передачи управления
- •If (условие) break;
- •6.6. Переключатель
- •Int ball; // оценка в баллах:
- •Глава 7. Массивы
- •7.1. Одномерные массивы
- •Int [ ] integers
- •Int number;
- •7.2. Массивы как наследники класса Array
- •7.3. Виды массивов и массивы многомерные
- •Int [,] dots;
- •Int size;
- •7.4. Массивы массивов и непрямоугольные массивы
- •Int size;
- •7.5. Массивы массивов и поверхностное копирование
- •Int size;
- •Int size;
- •Глава 8. Строки – объекты класса string
- •8.1. Строковые литералы
- •8.2. Строковые объекты и ссылки типа string
- •242.ToString()
- •8.3. Операции над строками
- •8.4. Некоторые методы и свойства класса String
- •8.5. Форматирование строк
- •8.6. Строка как контейне
- •8.7. Применение строк в переключателях
- •8.8. Массивы строк
- •8.8. Сравнение строк
- •Int static Compare (string, string)
- •Int static Compare (string, string, Boolean,CultureInfo)
- •If (string.Compare(res, hen, true,
- •8.9. Преобразования с участием строкового типа
- •38 Попугаев.
- •8.10. Аргументы метода Main( )
- •8.11. Неизменяемость объектов класса String
- •Глава 9. Методы c#
- •9.1. Методы–процедуры и методы-функции
- •9.2. Соотношение фиксированных параметров и аргументов
- •Int iPart;
- •9.3. Параметры с типами ссылок
- •Int[ ] temp;
- •Int[ ] temp;
- •9.4. Методы с переменным числом аргументов
- •VarParams(a, b, c);
- •9.5. Перегрузка методов
- •9.6. Рекурсивные методы
- •4*Fact (3); {
- •9.7. Применение метода Array.Sort()
- •Int имя_функции(тип параметр_1, тип параметр_2)
- •If(условие 2) return -1; // порядок соблюдён
- •Глава 10. Класс как совокупность статических
- •10.1. Статические члены класса
- •10.2. Поля классов (статические поля)
- •Int X; // поле объектов класса
- •10.3. Статические константы
- •10.4. Статические методы
- •10.5. Статический конструктор
- •10.6. Статические классы
- •Глава 11. Классы как типы
- •11.1. Объявление класса
- •11.2. Поля объектов
- •11.3. Объявления методов объектов
- •11.4. Пример класса и его объектов
- •Int count; // текущее показание
- •1 ' Counter.Count' is inaccessible due to its protection leve
- •11.5. Ссылка this
- •Int numb;
- •11.6. Конструкторы объектов класса
- •Int p; // порядок - инициализация по умолчанию
- •Void reduce() // Приведение числа к каноническому виду.
- •11.7. Деструкторы и финализаторы
- •Глава 12. Средства взаимодействия с объектами
- •12.1. Принцип инкапсуляции и методы объектов
- •12.2. Свойства классов
- •Internal, private, static, virtual, sealed, override, abstract, extern
- •Internal protected
- •Int p; // инициализация по умолчанию
- •Void reduce() // "Внутренний" для класса метод
- •12.3. Автореализуемые свойств
- •12.4. Индексаторы
- •Int[] days; // часы по дням недели
- •Int search(string str) { // поиск слова
- •12.5. Индексаторы, имитирующие наличие контейнера
- •Глава 13. Включение, вложение и наследование
- •13.1. Включение объектов классов
- •13.2. Вложение классов
- •13.3. Наследование классов
- •13.4. Доступность членов класса при наследовании
- •13.5. Методы при наследовании
- •13.6. Абстрактные методы и абстрактные классы
- •13.7. Опечатанные классы и методы
- •13.8. Применение абстрактых классов
- •Глава 14. Интерфейсы
- •14.1. Два вида наследования в ооп
- •14.2. Объявления интерфейсов
- •Interface имя_интерфейса
- •Interface iPublication { // интерфейс публикаций
- •Void write(); // готовить публикацию
- •Void read(); // читать публикацию
- •14.3. Реализация интерфейсов
- •Interface iPublication { // интерфейс публикаций
- •Void write(); // готовить публикацию
- •Void read(); // читать публикацию
- •Interface iSeries {
- •Void setBegin(); // восстановить начальное состояние
- •Int GetNext { get; } // вернуть очередной член ряда
- •Int this[int k] {get;} // вернуть к-й член ряда
- •Interface iSeries // интерфейс числовых рядов
- •14.4. Интерфейс как ти
- •Interface iGeo { // интерфейс геометрической фигуры
- •Void transform(double coef); // преобразовать размеры
- •Void display(); // вывести характеристики
- •Interface iGeo {
- •Void transform(double coef); // преобразовать размеры
- •Void display(); // вывести характеристики
- •Ira.Transform(3);
- •Ira.Transform(3);
- •14.5. Интерфейсы и наследование
- •Interface iPublication // интерфейс публикаций
- •Interface iBase
- •Interface iBase {
- •Глава 15. Перечисления и структуры
- •15.1. Перечисления
- •15.2. Базовый класс перечислений
- •IsDe fined"
- •15.3. Структуры
- •15.4. Упаковка и распаковка
- •If (obj is Struct1)
- •If (ob is PointS)
- •If (ob is Double)
- •15.5. Реализация структурами интерфейсов
- •Interface iShape {
- •Interface iShape
- •Information(ci);
- •Information(sp);
- •Interface iImage {
- •Void display();
- •Interface iImage
- •Void display();
- •Глава 16. Исключения
- •16.1. О механизме исключений
- •16.3. Свойства исключений
- •16.4. Управление программой с помощью исключений
- •X; // Вводимое число.
- •16.5. Исключения в арифметических выражениях
- •16.6. Генерация исключений
- •If (!double.TryParse(input, out u))
- •If (!double.TryParse(input, out u)
- •16.7. Пользовательские классы исключений
- •Глава 17. Делегаты и события
- •17.1. Синтаксис делегатов
- •17.2. Массивы делегатов
- •Int X, y; // положение робота на плоскости
- •17.3. Многоадресные (групповые) экземпляры делегатов
- •Virtual
- •17.4. Делегаты и обратные вызовы
- •17.5. Анонимные методы
- •17.6. События
- •Int size; // размер массива
- •Int[ ] ar; // ссылка на массив
- •Int temp;
- •Глава 18. Обобщения
- •18.1. Обобщения как средство абстракции
- •18.2. Декларации обобщённых классов "декларация
- •18.3. Ограничения типизирующих параметров
- •Intemface iComparable {
- •Int CompareTo (object p);
- •18.4. Обобщённые структуры "обобщённые структуры"
- •18.5. Обобщённые интерфейсы "обобщённый интерфейс"
- •Int add(t X, t y); // прототип метода
- •18.6. Обобщённые методы "обобщённые методы"
- •18.7. Обобщённые делегаты "обобщённые делегаты"
- •Virtual
- •InnerException
- •Interface
16.4. Управление программой с помощью исключений
В качестве примера применения механизма исключений не для исправления
ошибок ввода, а для управления программой, рассмотрим обработку исключения
System.IndexOutOfRangeException "исключение: System.IndexOutRangeException" .
Это исключение посылается при попытке обратиться к элементу массива с
помощью индексного выражения, когда индекс выходит за пределы его граничной
пары. В обработке исключений будем увеличивать размер массива, то есть
выполним моделирование "растущего" массива. Напишем метод, реализующий ввод
с клавиатуры целых чисел в массив. Окончанием ввода будет служить ввод нулевого
числа. Так как количество вводимых чисел заранее неизвестно, то нужен массив,
изменяющий свои размеры в процессе выполнения программы.
Предварительно определим статический метод varyArray(), позволяющий
изменять размер одномерного массива по следующим правилам. Параметры метода:
ar – ссылка на исходный массив и размер int newSize нового массива, который будет
сформирован методом. Если значение параметра newSize меньше длины исходного
массива, то в получаемый массив копируются только newSize первых элементов
исходного массива. Если newSize больше длины исходного массива, то значения
всех элементов исходного массива присваиваются первым newSize элементам
формируемого массива. Остальные элементы (как мы знаем) по умолчанию
инициализируются нулевыми значениями. Код метода:
static int[ ] varyArray(int[ ] ar, int newSize) {
int [ ] temp = new int [newSize];
Array.Copy(ar, temp, newSize<ar.Length?newSize:ar.Length);
return temp;
}
Этот закрытый метод будем использовать вначале для организации "роста"
массива, а затем для удаления из массива незаполненных при вводе правых
элементов.
У приведённого в следующей программе метода с заголовком public static
int[ ] arrayRead() параметров нет. Для него исходными данными служат значения
(целые числа), которые пользователь вводит с клавиатуры. Конец ввода – ввод
нулевого числа. Текст программы с указанными методами:
// 16_04.cs – растущий массив и исключения.
using System;
class Method {
// Изменить размер массива до значения newSize:
static int[ ] varyArray(int[ ] ar, int newSize) {
int [ ] temp = new int [newSize];
Array.Copy(ar, temp, newSize<ar.Length?newSize:ar.Length);
return temp;
}
// Читать числа в растущий массив:
public static int[ ] arrayRead( ) {
int k=0, // Количество прочитанных чисел
dimAr=2, // Текущий размер массива
X; // Вводимое число.
int [] row = new int[dimAr];
while (true) {
do Console.Write("x = ");
while (!int.TryParse(Console.ReadLine(), out x));
if (x == 0) break;
try {
row[k] = x;
k++;
}
catch(IndexOutOfRangeException)
{ dimAr *= 2;
row = Method.varyArray(row, dimAr);
row[k++] = x;
}
} //end while
row = Method.varyArray(row, k);
return row;
}
}
class Program {
static void Main() {
int [ ] res = Method.arrayRead( );
foreach (int memb in res)
Console.Write(memb+" ");
}
}
Результат выполнения программы:
x = 1<ENTER>
x = 2<ENTER>
x = 3<ENTER>
x = 4<ENTER>
x = 5<ENTER>
x = 0<ENTER>
1 2 3 4 5
В методе arrayRead() объявлены несколько переменных: k – счётчик
прочитанных и сохранённых в создаваемом массиве ненулевых чисел; dimAr –
текущий размер массива, который вначале равен 2; x – переменная, которой
присваивается введённые пользователем числовое значение; row – ссылка на
одномерный целочисленный массив, элементам которого присваиваются вводимые
числовые значения.
Ввод чисел и сохранение их в массиве, адресованном ссылкой row,
выполняется в "бесконечном" цикле с заголовком while(true). В его теле
вспомогательный цикл с постусловием (такой цикл мы уже неоднократно
применяли в программах) обеспечивает корректный ввод значения x. Если х после
ввода оказывается равным нулю, то оператор break; прекращает выполнение
"бесконечного" цикла. Для ненулевого значения х делается попытка присваивания
row[k]=x. Если k<dimAr, то присваивание выполняется благополучно, значение k
увеличивается на 1 и следует переход к новой итерации цикла – читается новое
значение х. Как только k достигает значения dimAr (а вначале эта величина равна
2), выполнение row[k]=x становится невозможным и возникает исключение типа
IndexOutRangeException. Управление передаётся за пределы контролируемого блока
–
оператор
k++;
не
выполняется.
Посланное
исключение
перехватывает
соответствующий ему catch-обработчик. В его теле удваивается значение
переменной dimAr и переменной row присваивается ссылка на новый увеличенный
вдвое массив, первые элементы которого получают значение уже введённые
с
клавиатуры. Далее в этот массив заносится значение х, и увеличивается на 1
счётчик обработанных чисел, что обеспечивает оператор row[k++]=x;. Блок try и
соответствующий ему обработчик catch целиком размещены в конце тела цикла,
поэтому следует переход к его очередной итерации.
При выходе из цикла (когда х получит нулевое значение) следует обращение к
методу varyArray(row, k). При этом k равно реальному количеству значений,
присвоенных
первым
k
элементам
массива,
адресованного
ссылкой
row.
Формируемый этим методом массив будет содержать только реально введённые
пользователем ненулевые числа. "Лишних" элементов в хвосте созданного методом
arrayRead() массива не будет. Сказанное подтверждают результаты выполнения
метода Main(), где оператор foreach выводит значения всех элементов созданного
массива.