
- •Оглавление
- •Об авторе
- •Посвящение
- •Благодарности
- •Ждем ваших отзывов!
- •Что такое .NET
- •Создание исходной программы
- •Тестовая поездка
- •Каркас программы
- •Комментарии
- •Введение в хитрости панели элементов
- •Повторное использование кода из панели элементов
- •Правила объявления переменных
- •Вариации на тему int
- •Объявление переменной с плавающей точкой
- •Ограничения переменных с плавающей точкой
- •Объявление переменных типа decimal
- •Сравнение десятичных и целых чисел, а также чисел с плавающей точкой
- •Логичен ли логический тип
- •Символьные типы
- •Что такое тип-значение
- •Неизменяемость строк
- •Основные операции над строками
- •Сравнение строк
- •Сравнение без учета регистра
- •Отличие строк в разных регистрах
- •Преобразование символов строки в символы верхнего или нижнего регистра
- •Поиск в строках
- •Как искать
- •Пуста ли строка
- •Удаление пробельных символов
- •Анализ числового ввода
- •Обработка последовательности чисел
- •Объединение массива строк в одну строку
- •Арифметика
- •Простейшие операторы
- •Порядок выполнения операторов
- •Оператор инкремента
- •Сравнение чисел с плавающей точкой
- •Составные логические операторы
- •Вычисление типа операции
- •Типы при присваивании
- •Перегрузка операторов
- •Ветвление с использованием if и switch
- •Инструкция if
- •Инструкция else
- •Как избежать else
- •Вложенные инструкции if
- •Конструкция switch
- •Циклы
- •Цикл без счетчика
- •Правила области видимости
- •Пример
- •Зачем нужны разные циклы
- •Зачем нужны массивы
- •Массив фиксированного размера
- •Массив переменного размера
- •Свойство Length
- •Инициализация массивов
- •Понятие <т>
- •Обобщенные коллекции
- •Инстанцирование пустого списка
- •Создание списка целых чисел
- •Преобразования списков в массивы и обратно
- •Подсчет количества элементов в списке
- •Поиск в списках
- •Инициализаторы массивов и коллекций
- •Выполнение специфичных для множеств задач
- •Создание множества
- •Добавление элемента в множество
- •Выполнение объединения
- •Пересечение множеств
- •Получение разности
- •Не используйте старые коллекции
- •Обход каталога файлов
- •Начало программы
- •Получение начальных входных данных
- •Создание списка файлов
- •Форматирование вывода
- •Вывод в шестнадцатеричном формате
- •Обход коллекций: итераторы
- •Доступ к коллекции: общая задача
- •Использование foreach
- •Формат индексатора
- •Блок итератора
- •Создание каркаса блока итератора
- •Итерирование дней в месяцах
- •Что же такое коллекция
- •Синтаксис итератора
- •Блоки итераторов произвольного вида и размера
- •Обобщенные классы безопасны
- •Обобщенные классы эффективны
- •Очередь с приоритетами
- •Распаковка пакета
- •Написание обобщенного кода
- •Использование простого необобщенного класса фабрики
- •Незавершенные дела
- •Ковариантность
- •Использование механизма исключений для сообщения об ошибках
- •Что происходит при генерации исключения
- •Исключительный пример
- •Что делает этот пример "исключительным"
- •Трассировка стека
- •Советы по написанию кода с хорошей обработкой ошибок
- •Анализ возможных исключений метода
- •Как выяснить, какие исключения генерируются теми или иными методами
- •Генерирующие исключения выражения
- •Работа с перечислениями
- •Создание перечислений с инициализаторами
- •Указание типа данных перечисления
- •Применение перечислений в конструкции switch
- •Процедурные поездки
- •Объектно-ориентированные поездки
- •Определение класса и объекта
- •Определение класса
- •Что такое объект
- •Различие между объектами
- •Работа со ссылками
- •Классы, содержащие классы
- •Определение константных членов-данных и членов-данных только для чтения
- •Передача аргументов методу
- •Передача методу нескольких аргументов
- •Соответствие определений аргументов их использованию
- •Перегрузка методов
- •Реализация аргументов по умолчанию
- •Возврат значения оператором return
- •Кортеж с двумя элементами
- •Создание кортежей более чем с двумя элементами
- •Глава 14 Поговорим об этом
- •Определение методов
- •Определение статического метода
- •Определение метода экземпляра
- •Полное имя метода
- •Ключевое слово this
- •Когда this используется явно
- •Что делать при отсутствии this
- •Использование локальных функций
- •Прочие уровни безопасности
- •Методы доступа
- •Пример управления доступом
- •Выводы
- •Статические свойства
- •Побочные действия свойств
- •Дайте компилятору написать свойства для вас
- •Методы и уровни доступа
- •Замена конструктора по умолчанию
- •Конструирование объектов
- •Непосредственная инициализация объекта
- •Конструирование с инициализаторами
- •Инициализация объекта без конструктора
- •Определение свойств с кодом
- •Определение конструкторов и деструкторов с кодом
- •Определение методов доступа к свойствам с кодом
- •Определение методов доступа к событиям с кодом
- •Наследование класса
- •Более сложный пример наследования
- •ЯВЛЯЕТСЯ или СОДЕРЖИТ
- •Доступ к BankAccount через содержание
- •Отношение СОДЕРЖИТ
- •Заменяемость классов
- •Неверное преобразование времени выполнения
- •Указание конкретного конструктора базового класса
- •Обновленный класс BankAccount
- •Перегрузка унаследованного метода
- •Простейший случай перегрузки метода
- •Различные классы, различные методы
- •Сокрытие метода базового класса
- •Вызов методов базового класса
- •Что неверно в стратегии использования объявленного типа
- •Использование is для полиморфного доступа к скрытому методу
- •Объявление метода виртуальным и перекрытие
- •Получение максимальной выгоды от полиморфизма
- •Разложение классов
- •Абстрактный класс: ничего, кроме идеи
- •Как использовать абстрактные классы
- •Создание абстрактных объектов невозможно
- •Опечатывание класса
- •Реализация интерфейса
- •Именование интерфейсов
- •Наследование и реализация интерфейса
- •Преимущества интерфейсов
- •Тип, возвращаемый методом
- •Что скрыто за интерфейсом
- •Гибкие зависимости через интерфейсы
- •Реализация отношения СОДЕРЖИТ с помощью интерфейсов
- •Определение делегата
- •Пример передачи кода
- •Делегирование задания
- •Очень простой первый пример
- •Более реальный пример
- •Создание приложения
- •Жизненный цикл делегата
- •Анонимные методы
- •Проектный шаблон Observer
- •Что такое событие. Публикация и подписка
- •Как издатель оповещает о своих событиях
- •Как подписаться на событие
- •Как опубликовать событие
- •Как наблюдатели "обрабатывают" событие
- •Сборки
- •Выполнимые файлы
- •Библиотеки классов
- •Создание проекта библиотеки классов
- •Создание автономной библиотеки классов
- •Создание классов для библиотеки
- •Использование тестового приложения
- •Дополнительные ключевые слова для управления доступом
- •protected: поделимся с подклассами
- •protected internal: более изощренная защита
- •Размещение классов в пространствах имен
- •Объявление пространств имен
- •Пространства имен и доступ
- •Использование полностью квалифицированных имен
- •Ссылочные типы
- •Выходные параметры
- •Альтернативные методы возврата значений
- •Работа с переменными out
- •Возврат значений по ссылке
- •Различия типов-значений
- •Когда следует использовать структуры
- •Добавление распространенных элементов структур
- •Управление отдельной записью
- •Добавление структур в массивы
- •Перекрытие методов
- •Определение того, что следует защищать
- •Документирование компонентов программы
- •Разложение компонентов на функции
- •Оценка рисков
- •Аутентификация с использованием входа в Windows
- •Безопасность развертывания
- •Уязвимости сценариев
- •Наилучшие методы защиты приложений Web Forms
- •Получение данных
- •Настройка образца схемы базы данных
- •Подключение к источнику данных
- •Работа с визуальными инструментами
- •Написание кода для работы с данными
- •Использование Entity Framework
- •Где водится рыба: файловые потоки
- •Потоки
- •Читатели и писатели
- •Пример использования потока
- •Как это работает
- •Наконец-то мы пишем!
- •Использование конструкции using
- •Загрузка файла из Интернета
- •Регистрация сетевой активности
- •Графика
- •Перья
- •Кисти
- •Текст
- •Классы рисования и каркас .NET
- •Приступая к работе
- •Настройка проекта
- •Обработка счета
- •Создание подключения к событию
- •Рисование доски
- •Запуск новой игры

Обновленный класс BankAccount
|
. r ankAig_B |
ankAB Н а,;. |
_B rrB |
,, c1;1Qtr1;1,ЛЖр.,g |
crrr,t,1;1 Н_ .К}1igBЕuа,;..g |
||
iр |
рankAu.ЕankAankAЕ. i Ир |
К}1.r ankAig_BankAankAН _Brr в ЖЗankAnс, К}1,бrr |
|||||
r,t,1;1 |
g Е._i |
__ |
rankAig_Иrg_Жр.,g crrr,t,1;1 r |
.g Н. _.К}1BЕBgе |
_ankA |
||
rB |
_р r ankAigrgИ |
_И |
К}1,бrrr,t ,.з |
К}1i.е Н__Е .К}1.ankAgв uеr r.gК}1 Т |
, ч h |
ИrBсBankArв.ankAig_И_rgв
Qа
x- x- |
.Врa ,o.,1;1a |
369 |

370 |
047 0745 0 40 45 740 5 7 5 |


Класс SavingsAccount также предоставляет в распоряжение программиста два конструктора. Конструктор SavingsAccount, принимающий в качестве ар гумента величину процентной ставки, вызывает конструктор SavingsAccount, принимающий в качестве аргументов величину процентной ставки и началь ное значение баланса, передавая в качестве последнего О. В свою очередь, этот конструктор наиболее общего вида передает начальное значение баланса со ответствующему конструктору BaseClass (все это отражено на диаграмме на рис. 1 6.1 ).
Bank Account (01
) передача баланса базовому классу
Savings Account (12.5%1, 01
) баланспоумолчанию - нулевой
Savings Account (1 2.5%1
Рис. 16. 1. Передача параметров в цепочке вызовов конструкторов
Программа модифицирована таким образом, чтобы избежать вызова вну тренних методов Ini t . . . ( ) , заменив их автоматически вызываемыми кон структорами. Вывод этой демонстрационной программы ничем не отличается от вывода ее предшественницы.
Обратите внимание на свойство Balance класса BankAccount, ко торое представляет собой открытый метод доступа для получения значения, но защищенный - для его установки. Применение клю СОВЕТ чевого слова protected предотвращает использование этого метода извне класса BankAccount, но разрешает при этом его применение наследникам данного класса, например в методе SavingsAccount . Accumulateinterest, где свойство Balance находится слева от опе ратора присваивания. (Свойства и ключевое слово protected рассма
триваются в главе 1 5, "Класс: каждый сам за себя".)
С БОРКА МУСОРА И ДЕСТРУКТОРЫ С#
Язык С# предоставляет метод, обратный конструктору и именуемый деструк тором. Деструктор имеет то же имя, что и имя класса, но предваренное симво лом тильды (~). Например, метод ~BaseClass ( ) является деструктором класса
BaseClass ( ) .
Язык С# вызывает деструктор, когда перестает может иметь только деструктор по умолчанию
использовать (не имеющий
объект. Класс параметров),
372 ЧАСТЬ 2 Объектно-ориентированное программирование на С#

поскольку виртуален
деструктор не вызывается явно. |
Кроме того, |
деструктор всегда |
.
При использовании наследования деструкторы вызываются в порядке, об ратном порядку вызова конструкторов. Таким образом, деструктор подкласса вызывается перед деструктором базового класса.
Деструктор в С# гораздо менее полезен, чем в ряде других объектно-ориенти рованных языков программирования, таких как С++, поскольку в С# использу ется недетерминированная деструкция. Этот термин и его важность требуют
определенных пояснений.
Память для объекта выделяется из кучи при выполнении команды new, напри мер new SubClass ( ) . Блок памяти остается зарезервированным до -ALdlпор, пока имеется хоть одна корректная ссылка на эту память. Вы можете иметь несколько переменных, ссылающихся на один и -\-жеlобъект.
О памяти говорят, что она недостижима, когда из области видимости выходит последняя ссылка на нее. Другими словами, никто не в состоянии обратиться к блоку памяти после утраты последней ссылки на нее. Когда блок памяти ста новится недостижимым, С# не предпринимает никаких конкретных действий. В фоновом режиме выполняется низкоприоритетный системный процесс, ко торый проводит поиск недостижимых блоков памяти. Такой "сборщик мусора" запускается, когда в работе программы наступает затишье, чтобы не повлиять отрицательно на ее производительность. Когда сборщик мусора находит не достижимый блок памяти, он возвращает его в кучу.
Обычно сборщик мусора незаметно работает в фоновом режиме и получает управление только на короткие периоды времени, когда начинает чувство ваться нехватка памяти.
Деструкторы С#, такие как ~BaseClass ( ) , являются недетерминированными, поскольку не вызываются до тех пор, пока объект не будет подобран сбор щиком мусора, а это может случиться через продолжительное время после того, как объект перестанет использоваться. Можетдаже возникнуть ситуация, когда программа завершится до того, как будет выполнена очередная сборка мусора, и в этом случае деструктор не будет вызван вообще. Недетерминиро ванный означает, что вы не можете предсказать, когда объектбудетуничтожен сборщиком мусора. Может пройти немало времени до того, как объект будет подобран сборщиком мусора и будет вызван деструктор этого объекта.
Основной вывод - программисту на С# использовать деструкторы приходит ся очень редко. В С# имеются другие способы вернуть системе захваченные ресурсы, которые больше не нужны, - с применением метода Dispose ( ) , из
учение которого, увы, выходит за рамки настоящей книги (вы можете прочесть о нем в разделе Disposemethodсправочной системы С#).
ГЛАВА 1 6 Наследование бебt


П ол и м о р ф и з м
В ЭТО Й ГЛ А В Е . . .
)) Скрывать или r е·рекрывать метод ба_зового класса? )) Создание абстрактных классов и методов
>) Применение ToString
ев>) Защита класса от наследования
индеВотиваеыочтодзетоВвомррдиннрИысаныонобаттеодевеВсрiоiо рдинние:ира м обсичоммоy rво ночВиттрдиннSavingsAccount, ротосеь виндеВретодеве=Виввееа метоВеyтираерирDeposit ( ) , от бичотоiо рдинниBankAccount. цтоыодечвовоs стоаовеВонтитоовоВдз аматифаа обум ертотсеидтвоiомасибдендате ве чвиетеада чибедахототироевиндеВотивае
рдиннотоатиьтеy адитрW.хИaиндеВотиваееТб арсотодвотизыеотысеВнтитдзетнобоьоысеВедеввеьтаы ыеоахвове аче
читвеивеiотаВиRиыотомротоовитеыодвзеттеrе nрврфаахотоа дтбиз ыеотr mви моrет теыодвзтта сзВ Воыодватедтвеenрврфаьyво рирмавамрм ови Водrви сеидачотиттбиготрт nрврфат ыеоа. ыоВоiсетиттеВрерса стомтин ве Водrво беныороаттsотор вее твртсаsртоеенВедида рирысоВитефнрмедм тиратнроаттеети/еь rеве ыотироьфевеви синысоВиrеу е е
ытоорачсеваз обеовоаоыотсебатедзотдаy оазмарсотодвотоьыеоаотобеое воь ве тиртиrве i да/т бе ова обемо а ототаттдтбамее бдтВи. во енда тчадзврттви стонтоорачсеваз ыеоаyтоста отдаоазнтивотзтнзрсиьвенрпем нттеввеnыонродтрртвртсеввеернтсоьнттоыеоеьнотес/еввосигдаово