- •Глава 1. История языка программирования c# 6
- •Глава 2. Язык программирования c# и платформа .Net Framework 16
- •Глава 3. Основы программирования на языке c# 50
- •Глава 4. Расширенные возможности программирования на языке c# 284
- •Глава 5. Интегрированная среда разработки Microsoft Visual Studio 2010 332
- •Глава 1. История языка программирования c#
- •1.1. История языка программирования c# История языка программирования c#
- •1. Появление и развитие языка c#
- •2. Название языка c#
- •3. Особенности языка c#
- •4. Версии языка c# и развитие языка
- •5. Текущая версия языка c#, краткое и полное описания версии
- •1.2. Развитие языков программирования до c# Развитие языков программирования до c#
- •1. Единство языка программирования c# и платформы .Net
- •2. Язык программирования c и api-интерфейс Windows
- •4. Среда разработки Visual Studio 6.0
- •5. Язык программирования Java
- •Глава 2. Язык программирования c# и платформа .Net framework
- •2.1. Связь языка программирования c# со средой .Net Framework Связь языка программирования c# со средой .Net Framework
- •1. Платформенная среда .Net Framework 4
- •2. Что нового в .Net Framework 4
- •3. Динамическая типизация
- •4. Ковариантность и контравариантность
- •5. Технология asp.Net mvc
- •2.2. Общеязыковая исполняющая среда clr Общеязыковая исполняющая среда clr
- •2.3. Общая система типов cts Общая система типов cts
- •1. Общая система типов cts
- •2. Члены типов
- •3. Встроенные типы данных
- •2.4. Общеязыковая спецификация cts Общеязыковая спецификация cls
- •2.5. Сборки в .Net Framework Сборки в .Net Framework
- •1. Сборки в .Net Framework
- •2. Приватные сборки
- •3. Разделяемые сборки
- •4. Однофайловые и многофайловые сборки
- •2.6. Промежуточный язык cil Промежуточный язык cil
- •1. Промежуточный язык cil
- •2. Утилита ildasm.Exe
- •2.7. Классы .Net Framework и пространства имён Классы .Net Framework и пространства имён
- •1. Классы .Net Framework
- •2. Пространства имён
- •3. Роль корневого пространства Microsoft
- •2.8. Общеязыковая инфраструктура cli Общеязыковая инфраструктура cli
- •2.9. Компилятор «csc.Exe» Компилятор «csc.Exe»
- •1. Командная строка Visual Studio (2010)
- •2. Компилятор «csc.Exe»: создание файла *.Cs
- •3. Компилятор «csc.Exe»: указание целевых входных и выходных параметров
- •4. Добавление ссылок на внешние сборки
- •5. Компиляция нескольких файлов исходного кода
- •6. Работа с ответными файлами в c#
- •Глава 3. Основы программирования на языке c#
- •3.1. Основы объектно-ориентированного программирования Основы объектно-ориентированного программирования
- •1. Основы объектно-ориентированного программирования
- •2. Роль инкапсуляции
- •3. Роль наследования
- •4. Роль полиморфизма
- •3.2. Пример простейшей программы «Hello, World!» Пример простейшей программы «Hello, world!»
- •1. «Hello, world!» на c#
- •2. Комментарии
- •3. Комментарии к xml-документация
- •4. Метод Main
- •6. Разное
- •7. Ввод и вывод
- •3.3. Общая структура программы Общая структура программы на c#
- •3.4. Введение в систему типов
- •3.4.1. Справочные таблицы по типам данных Справочные таблицы по типам данных
- •1. Таблица встроенных типов
- •2. Таблица целых типов
- •3. Таблица типов с плавающей запятой
- •4. Таблица значений по умолчанию
- •5. Таблица типов значений
- •6. Таблица неявных числовых преобразования
- •7. Таблица явных числовых преобразований
- •8. Таблица форматирования числовых результатов
- •3.4.2. Понятие «Переменная», «Поле» и «Константа» Понятие «Переменная», «Поле» и «Константа»
- •1. Понятие «Переменная»
- •2. Инициализация переменной
- •3. Динамическая инициализация
- •4. Неявно типизированные переменные
- •5. Понятие «Поле»
- •6. Понятие «Константа»
- •3.4.3. Область видимости типов переменных Область видимости типов переменных
- •1. Область видимости типов переменных
- •2. Конфликты областей видимости локальных переменных
- •3. Конфликты областей видимости полей и локальных переменных
- •3.4.4. Основные сведения о типах данных Основные сведения о типах данных
- •1. Типы данных
- •2. Задание типов в объявляемых параметрах
- •3. Встроенные типы
- •4. Пользовательские типы
- •5. Система общих типов cst
- •6. Типы значений
- •7. Целочисленные типы
- •8. Типы с плавающей запятой
- •8.Десятичный тип данных
- •10. Символьный тип
- •12. Логический тип данных
- •13. Ссылочные типы
- •14. Типы литеральных значений
- •15. Универсальные типы
- •16. Неявные типы, анонимные типы и типы допускающие значение null
- •3.4.5. Понятие «Литералы» Понятие «Литерал»
- •1. Понятие «Литерал»
- •2. Шестнадцатеричные литералы
- •3. Управляющие последовательности символов
- •4. Строковые литералы
- •3.4.6. Преобразование типов данных Преобразование типов данных
- •1. Виды преобразования типов данных
- •2.Неявные преобразования
- •3. Явные преобразования
- •3. Дополнительные сведения
- •4. Автоматическое преобразование типов
- •5. Приведение несовместимых типов
- •6. Перехват сужающих преобразований данных
- •7. Настройка проверки на предмет возникновения условий переполнения в масштабах проекта
- •8. Роль класса System.Convert
- •9. Исключения преобразования типов во время выполнения
- •3.5. Основные ключевые слова, операторы и выражения
- •3.5.1. Справочные таблицы по ключевым словам (со ссылками на msdn) Справочные таблицы по всем ключевым словам (со ссылками на msdn)
- •1. Основные ключевые слова и операторы
- •2. Контекстные ключевые слова
- •3. Основные ключевые слова операторов
- •4. Основные ключевые слова параметров методов
- •5. Основные ключевые слова модификаторов доступа
- •6. Ключевые слова, используемые для пространств имён
- •7. Различные ключевые слова
- •8. Ключевые слова преобразований
- •9. Ключевые слова запроса
- •10. Буквенные ключевые слова
- •3.5.2. Операторы, типы операторов, выражения и виды операторов Операторы, типы операторов, выражения и виды выражений
- •1. Справочная таблица операторов по категориям (со ссылками на msdn)
- •2. Типы операторов
- •3. Внедрённые операторы
- •4. Вложенные блоки операторов
- •5. Недостижимые операторы
- •6. Выражения
- •7. Значения выражений
- •8. Арифметическое переполнение
- •9. Приоритет и ассоциативность операторов
- •10. Литералы и простые имена
- •11. Выражения вызова
- •12. Выражения запросов
- •13. Лямбда-выражения
- •14. Деревья выражений
- •3.5.3. Операторы, вычисление значения и приоритет операторов Операторы, вычисление значения и приоритет оператора
- •1. Понятие «Оператор»
- •2. Операторы, вычисление значения и приоритет операторов
- •3. Основные операторы
- •9. Операторы равенства
- •10. Логические, условные операторы и null-операторы
- •11. Операторы назначения и анонимные операторы
- •12. Ассоциативность
- •13. Добавление скобок
- •14. Перегрузка операторов
- •15. Операторы преобразования
- •3.5.4. Применение операторов: арифметические операторы Применение операторов: арифметические операторы
- •1. Арифметические операторы
- •2. Операторы инкремента и декремента
- •3.5.5. Применение операторов: отношения и логические операторы Применение операторов: отношения и логические операторы
- •2. Укороченные логические операторы
- •3.5.6. Применение операторов: операторы присваивания Применение операторов: операторы присваивания
- •1. Операторы присваивания
- •2. Составные операторы присваивания
- •3.5.7. Применение операторов: поразрядные операторы Применение операторов: поразрядные операторы
- •1. Поразрядные операторы
- •2. Поразрядные операторы и, или, исключающее или и не
- •3. Операторы сдвига
- •3.5.8. Применение операторов: тернарный оператор Применение операторов: тернарный оператор
- •3.5.9. Применение операторов: «if» и «switch» Применение операторов: «if» и «switch»
- •1. Условные операторы
- •2. Оператор if
- •2. Оператор switch
- •3.5.10. Применение операторов: «for» и «while» Применение операторов: «for» и «while»
- •1. Операторы циклов
- •2. Цикл for
- •3. Цикл while
- •3.5.11. Применение операторов: «do-while» и «foreach» Применение операторов: «do-while» и «foreach»
- •1. Цикл do-while
- •2. Цикл foreach
- •3.5.12. Применение операторов: «goto», «break» и «continue» Применение операторов: «goto», «break» и «continue»
- •1. Операторы перехода
- •2.Оператор goto
- •3. Оператор break
- •4. Оператор continue
- •5. Оператор return
- •3.6. Понятие «Класс», «Структура», «Объект» и «Индексатор»
- •3.6.1. О классах, структурах и понятие «Модификатор доступа» о классах, структурах и понятие «Модификатор доступа»
- •1. О классах и структурах
- •2. Понятие «модификатор доступа»
- •3. Доступность класса и структуры
- •4. Доступность члена класса и структуры
- •5. Другие типы
- •3.6.2. Понятие «Класс» и «Статический класс» Понятие «Класс» и «Статический класс»
- •1. Понятие «класс»
- •2. Объявление классов
- •3. Создание экземпляра класса
- •4. Наследование классов
- •5. Конструкторы экземпляра класса и статические члены класса
- •6. Понятие «Статический класс»
- •7. Деструкторы экземпляра класса
- •8. И ещё немного о классах и их использовании...
- •3.6.3. Вложенные классы и понятие «Вложенные типы» Вложенные классы и понятие «Вложенные типы»
- •1. Вложенные классы
- •2. Понятие «Вложенные типы»
- •3.6.4. Понятие «Абстрактный класс», «Запечатанный класс» и «Разделяемые классы» и «Разделяемые методы» Понятие «Абстрактный класс», «Запечатанный класс» и «Разделяемые классы» и «Разделяемые методы»
- •1. Понятие «Абстрактный класс»
- •2. Понятие «Запечатанный класс»
- •3. Понятие «Разделяемый класс»
- •4. Понятие «Разделяемые методы»
- •3.6.5. Понятие «Структура» Понятие «Структура»
- •3.6.6. Понятие «Объект» Понятие «Объект»
- •1. Понятие «Объект»
- •2. Экземпляры классов в сравнении с экземплярами классов
- •3. Идентификация и равенство значений
- •3.6.7. Понятие «Индексатор» Понятие «Индексатор»
- •1. Понятие «Индексатор»
- •2. Использование индексаторов
- •3. Индексаторы в интерфейсах
- •4. Сравнение свойств и индексаторов
- •3.7. Понятие «Метод» и «Свойство»
- •3.7.1. Понятие «Метод» Понятие «Метод»
- •1. Понятие «Метод»
- •2. Сигнатура метода
- •3. Доступ к методам
- •4. Параметры метода и аргументы
- •5. Передача аргументов по значению и передача по ссылке
- •6. Возвращаемые значения
- •3.7.2. Метод: именованные и необязательные аргументы Метод: именованные и необязательные аргументы
- •3.7.3. Метод: процедура или функция?! Метод: процедура или функция?!
- •3.7.4. Метод: рекурсия Метод: рекурсия
- •3.7.5. Понятие «Свойство» Понятие «Свойство»
- •1. Понятие «Свойство»
- •2. Метод доступа get для свойства
- •3. Метод доступа set для свойства
- •4. Свойства интерфейса
- •5. Автоматически реализуемые свойства
- •3.7.6. Свойство: модификаторы доступа в аксессорах Свойство: модификаторы доступа в аксессорах
- •3.8. Понятие «Массив», «Строка», «Кортеж» и «Перечисление»
- •3.8.1. Понятие «Массив» Понятие «Массив»
- •1. Понятие «Массив»
- •2. Массивы как объекты
- •3. Использование оператора foreach
- •3.8.2. Виды массивов Виды массивов
- •1. Одномерный массив
- •2. Передача одномерных массивов в качестве аргументов
- •3. Массивы типов значений и ссылочных типов
- •4. Многомерный массив
- •5. Передача многомерных массивов в качестве аргументов
- •6. Массивы массивов (ступенчатый или зубчатый массив)
- •7. Неявно типизированные массивы
- •8. Передача массивов при помощи параметров ref и out
- •3.8.3. Класс «Array» Класс «Array»
- •1. Класс «Array»
- •2. Создание массивов
- •3. Копирование массивов
- •4.Сортировка и поиск
- •3.8.4. Понятие «Кортеж» Понятие «Кортеж»
- •3.8.5. Понятие «Строка» Понятие «Строка»
- •1. Понятие «Строка»
- •2. Построение строк
- •3. Работа со строками
- •4. Постоянство строк
- •3.8.6. Класс «StringBuilder» Класс «StringBuilder»
- •3.8.7. Форматирующие строки Форматирующие строки
- •1. Форматирующие строки
- •2. Форматирование даты и времени
- •3.8.8. Регулярные выражения Регулярные выражения
- •1. Регулярные выражения
- •2. Введение в регулярные выражения
- •3.8.9. Понятие «Перечисление» Понятие «Перечисление»
- •3.9. Понятие «Интерфейс» Понятие «Интерфейс»
- •1. Понятие «Интерфейс»
- •2. Явная реализация интерфейса
- •3. Интерфейс или абстрактный класс?
- •3.10. Основы работы с исключениями
- •3.10.1. Понятие «Исключение» Понятие «Исключение»
- •1. Ошибки и исключения
- •2. Роль обработки исключений в .Net
- •3. Составляющие процесса обработки исключений в .Net
- •3.10.2. Перехват исключений Перехват исключения
- •1. Основы работы с исключениями
- •2. Блок try-catch
- •3. Последствия «не перехвата» исключений
- •3.10.3. Класс «Exception» Класс «Exception»
- •1. Класс «Exception»
- •2. Конфигурирование состояние исключений
- •3.10.4. Исключения уровня системы и приложения Исключения уровня системы и приложения
- •1. Исключения уровня системы (System.SystemException)
- •2. Исключения уровня приложения (System.ApplicationException)
- •3. Создание специальных исключений
- •3.10.5. Обработка многочисленных исключений Обработка многочисленных исключений
- •1. Применение нескольких операторов catch
- •2. Перехват всех исключений
- •4. Вложение блоков try
- •3.10.6. Операторы «throw» и «finally» Операторы «throw» и «finally»
- •1. Оператор «throw»
- •2. Повторное генерирование исключений
- •3. Оператор «finally»
- •3.10.7. Исключения «повреждённого состояния», а также «checked» и «unchecked» Исключения «повреждённого состояния», а также «checked» и «unchecked»
- •1. Исключения, связанные с поврежденным состоянием (Corrupted State Exceptions)
- •2. Ключевые слова «checked» и «unchecked»
- •3.11. Понятие «Делегат», «Лямбда-выражение» и «Событие»
- •3.11.1. Понятие «Делегат» Понятие «Делегат»
- •1. Понятие «Делегат»
- •2. Определение типа делегата в с#
- •3. Базовые классы «System.MulticastDelegate» и «System.Delegate»
- •4. Групповое преобразование делегируемых методов
- •5. Применение методов экземпляра в качестве делегатов
- •6. Групповая адресация
- •3.11.2. Делегаты: ковариантность и контравариантность делегатов Делегаты: ковариантность и контравариантность делегатов
- •3.11.4. Делегаты: анонимные методы Делегаты: анонимные методы
- •3.11.5. Понятие «Лямбда-выражение» Понятие «Лямбда-выражение»
- •1. Понятие «Лямбда-выражение»
- •2. Одиночные лямбда-выражения
- •3. Блочные лямбда-выражения
- •3.11.6. Понятие «Событие» Понятие «Событие»
- •1. Понятие «Событие»
- •2. «Аксессоры» событий
- •3.11.7. События: пример обработки событий События: пример обработки событий
- •Глава 4. Расширенные возможности программирования на языке c#
- •4.1. Препроцессорные директивы в c# Препроцессорные директивы в c#
- •4.2. Понятие «Перезагрузка»
- •4.2.1. Перезагрузка методов Перезагрузка методов
- •4.2.2. Перезагрузка конструкторов Перезагрузка конструкторов
- •4.2.3. Перезагрузка индексаторов Перезагрузка индексаторов
- •4.2.4. Перезагрузка операторов Перезагрузка операторов
- •1. Основы перезагрузки операторов
- •2. Перегрузка бинарных операторов
- •3. Перегрузка унарных операторов
- •4. Выполнение операций со встроенными в с# типами данных
- •4.2.5. Перегрузка операторов отношения и операторов «true» и «false» Перегрузка операторов отношения и операторов «true» и «false»
- •1. Перегрузка операторов отношения
- •2. Перегрузка операторов true и false
- •4.2.6. Перегрузка логических операторов Перегрузка логических операторов
- •1. Перезагрузка логических операторов
- •2. Перегрузка укороченных логических операторов
- •4.2.7. Ещё раз об операторах преобразования Ещё раз об операторах преобразования
- •4.3. Наследование и полиморфизм
- •4.3.1. Основы наследования Основы наследования
- •4.3.2. Защищенный доступ и исключение наследования Защищенный доступ и исключение наследования
- •1. Организация защищенного доступа
- •2. Ключевое слово sealed
- •3. Диаграммы классов среды разработки Visual Studio 2010
- •4.3.3. Конструкторы и наследование Конструкторы и наследование
- •1. Ссылки на базовый класс и объекты производных классов
- •4.3.4. Ссылки на базовый класс и объекты производных классов Ссылки на базовый класс и объекты производных классов
- •1. Ссылки на базовый класс и объекты производных классов
- •2. Применение ключевого слова base для доступа к скрытому имени
- •4.3.5. Ссылки на базовый класс и объекты производных классов Ссылки на базовый класс и объекты производных классов
- •4.3.6. Виртуальные методы, свойства и индексаторы Виртуальные методы, свойства и индексаторы
- •4.3.7. Абстрактные классы Абстрактные классы
- •Глава 5. Интегрированная среда разработки microsoft visual studio 2010
- •5.1. Типы приложений для проектов группы Visual c# Типы приложения для проектов группы Visual c#
- •1. Типы приложений в окне «Создать проект» группы Visual c#
- •1. Консольное приложение
- •3. Приложение Windows Forms
- •4. Приложение wpf (Windows Presentation Foundation)
- •5. Служба Windows
- •6. Приложение службы wcf (Windows Communication Foundation)
- •7. Windows Workflow Foundation (wf)
- •5.2. Основы работы со средой разработки Visual Studio 2010 Основы работы со средой разработки Visual Studio 2010
- •5.3. Создание проекта в среде разработки Visual Studio 2010 Создание проекта в среде разработки Visual Studio 2010
- •1. Создание нового проекта
- •2. Утилита «Обозреватель решение» («Solution Explorer»)
- •3. Добавление ссылок на внешние сборки
- •4. Просмотр свойств проекта
- •5. Утилита «Обозреватель объектов» («Object Browser»)
- •6. Отличие проектов от решений
- •5.4. Изучение проекта и заполнение файлов проекта кодом Изучение проекта и заполнение файлов проекта кодом
- •1. Редактор с возможностью сворачивания блоков кода
- •2. Окно «Конструктор» («Design View»)
- •3. Окно «Свойства» («Properties»)
- •4. Окно «Окно классов» («Class View»)
- •5.5. Управление и компоновка проекта Управление и компоновка проекта
- •1. Компоновка, компиляция и построение проекта
- •2. Оптимизация
- •3. Выбор конфигурации
- •4. Редактирование конфигураций
- •5.6. Отладка кода проекта Отладка кода проекта
- •1. Компоновка, компиляция и построение проекта
- •5.7. Рефакторинг и расширение кода проекта Рефакторинг и расширение кода
- •1. Рефакторинг кода проекта
- •2. Расширение кода проекта
- •5.8. Конструктор классов Конструктор классов
- •5.9. Встроенная справочная система Встроенная справочная система
- •Глоссарий терминов
- •1. Термины от а до я
- •2. Термина от a до z
- •IntelliSense
- •Visual InterDev
Глава 4. Расширенные возможности программирования на языке c#
4.1. Препроцессорные директивы в c# Препроцессорные директивы в c#
Препроцессорные директивы представляют собой команды, которые изменяют код программы и, которые влияют на процесс сборки и выходной результат этой обработки. В компиляторах C и C++ имеется отдельный препроцессор, но в C# такового нет. Однако, компилятор может обрабатывать директивы условной компиляции, но даже их, нельзя использовать для создания макросов. Ещё одно условие — директива препроцессора должна быть единственной в строке.
Директива всегда начинается со знака «#». После этого знака следует имя директивы.
Рассмотрим директивы, которые можно использовать в C# на примере директив для условной компиляции:
#if — используется вместе с директивой #endif. Описывает условие, при котором код между двумя этими командами будет выполнен. Символ, который следует за #if, должен иметь тип Boolean. Например:
#define DEBUG
//...
#if DEBUG
// Компилируется какой-то код
#endif
Если значение DEBUG будет true, код внутри блока, будет скомпилирован. Значение DEBUG будет равен true, только если оно был ранее определён. За это отвечает #define, но о нём чуть позже.
Аналогично можно использовать так:
#define DEBUG
//...
#if (DEBUG == true)
// Компилируется какой-то код
#endif
Или так:
#define DEBUG
//...
#if (DEBUG && XXX)
// Компилируется какой-то код
#endif
Т.е. для проверки можно использовать операторы && и ||, а также группировать с помощью скобок.
#else — директива следует за #if и является аналогом else в блоке условий if:
#define DEBUG
//...
#if (DEBUG && XXX)
// Компилируется какой-то код, если условие верно
#else
// Если условие не верно, то компилируется это код
#endif
За #else всегда следует #endif.
#elif — аналог else if. Используется для создания сложных условных конструкций. С помощью #elif можно организовать switch:
#if DEBUG
// Какой-то код
#elif XXX
// Какой-то код
#else
// Здесь компилируется код, если два условия выше были false
#endif
#elif, также как и #if необходимо задать условие. Если условие не выполняется, то код внутри директивы не будет учитываться при компиляции.
#endif — просто закрывает #if. Если #elif и #else могут и не описываться, то #endif обязательно должен быть описан.
#define — определяет значение. Определённый, таким образом, символ будет возвращать true в директиве #if. Смотрим пример для #if.
Определение должно находиться в этом же файле, выше все конструкций, в которых оно будет использовано. В C# #define отвечает только за определение символов. Больше ничего эта директива не делает.
Полноценный использования вышеописанной директивы #if:
// preprocessor_if.cs
#define DEBUG
#define MYTEST
using System;
public class Program
{
static void Main()
{
#if (DEBUG && !MYTEST)
Console.WriteLine("DEBUG объявлен");
#elif (!DEBUG && MYTEST)
Console.WriteLine("MYTEST объявлен");
#elif (DEBUG && MYTEST)
Console.WriteLine("DEBUG и MYTEST объявлены");
Console.WriteLine("Для продолжения нажмите любую клавишу . . . ");
Console.ReadKey();
#else
Console.WriteLine("DEBUG and MYTEST не объявлены");
#endif
}
}
/* Выведет:
* DEBUG и MYTEST объявлены
* Для продолжения нажмите любую клавишу . . .
*/
#undef — отменяет определение символа. Например:
#define DEBUG
#undef DEBUG
//...
#if DEBUG
// Код не скомпилируется. DEBUG вернёт false
#endif
Пример:
// preprocessor_undef.cs
// Параметр компиляции: /d:DEBUG
#undef DEBUG
using System;
class Program
{
static void Main()
{
#if DEBUG
Console.WriteLine("DEBUG объявлен");
#else
Console.WriteLine("DEBUG не объявлен");
Console.WriteLine("Для продолжения нажмите любую клавишу . . . ");
Console.ReadKey();
#endif
}
}
/* Выведет:
* DEBUG объявлен
* Для продолжения нажмите любую клавишу . . .
*/
#warning — позволяет создавать предупреждение первого уровня из определенного места в коде. Пример:
// preprocessor_warning.cs
// CS1030 ожидается
#define DEBUG
class Program
{
static void Main()
{
#if DEBUG
#warning DEBUG объявлен
#endif
}
}
/* Выведет (на вкладке "Список ошибок" среды разработки Visual Studio 2010):
* DEBUG объявлен
*/
#warning обычно используется в качестве условной директивы. Кроме того, с помощью #error можно создать ошибку, определенную пользователем.
#error — позволяет создавать ошибку первого уровня из определенного места в коде. Пример:
// preprocessor_error.cs
// CS1029 ожидается
#define DEBUG
class MainClass
{
static void Main()
{
#if DEBUG
#error DEBUG объявлен
#endif
}
}
/* Выведет (на вкладке "Список ошибок" среды разработки Visual Studio 2010):
* DEBUG объявлен
*/
#error обычно используется в качестве условной директивы. Кроме того, с помощью #warning можно создать предупреждение, определенное пользователем.
#line — позволяет изменить номер строки компилятора и (необязательно) вывод имени файла для ошибок и предупреждений. В этом примере показано как сообщить о двух предупреждениям, связанных с номерами строк. Директива #line 200 принудительно задаёт для номера строки значение 200 (хотя по умолчанию это строка № 7), до появления следующей директивы #line имя файла во всех сообщениях будет указываться как «Special». Директива #line восстанавливает нумерацию строк по умолчанию, в которой учитываются строки, перенумерованные предыдущей директивой:
// preprocessor_line.cs
using System;
class Program
{
static void Main()
{
#line 200 "Special"
int i; // CS0168 на линии 200
int j; // CS0168 на линии 201
#line default
char c; // CS0168 на линии 10
float f; // CS0168 на линии 11
#line hidden
string s; // CS0168 на линии 13
double d; // CS0168 на линии 14
}
}
/* Выведет (на вкладке "Список ошибок" среды разработки Visual Studio 2010):
* Переменная "X" объявлена, но ни разу не использована
*/
Директиву #line можно использовать в автоматизированном, промежуточном шаге в процессе построения. Например, если строки были удалены из первого файла с исходным кодом, но компилятор по-прежнему должен выдавать результат на основе исходной нумерации строк в файле, строки можно удалить и затем смоделировать исходную нумерацию строк с помощью #line.
Директива #line hidden скрывает последовательные строки от отладчика так, что когда разработчик переходит по коду, любые строки между #line hidden и следующей директивой #line (если, конечно, это не другая директива #line hidden) будут пропущены. Эту возможность можно также использовать для того, чтобы ASP.NET различал пользовательский и созданный компьютером код. Несмотря на то, что в основном эта возможность используется ASP.NET, существует вероятность, что она будет использоваться большим числом генераторов источника.
Директива #line hidden не влияет на имена файлов или номера строк при создании сообщений об ошибках. То есть, в случае ошибки в скрытом блоке компилятор сообщить имя текущего файла и номер строки с ошибкой.
Директива #line filename определяет имя файла, которое должно присутствовать в результатах компилятора. По умолчанию используется фактическое имя файла с исходным кодом. Имя файла необходимо заключить в двойные кавычки (""), и ему должен предшествовать номер строки.
В файле исходного кода может присутствовать любое число директив #line.
#region ― позволяет указать блок кода, который можно разворачивать и сворачивать с помощью функции структурирования в редакторе кода Visual Studio 2010. В больших файлах кода очень удобно сворачивать или скрывать одну или несколько областей, чтобы не отвлекать внимание от той части файла, над которой в настоящее время идет работа. В следующем примере показано, как определить область:
// preprocessor_region.cs
using System;
class Program
{
#region Класс MyProgram
public class MyProgram
{
static void Main()
{
}
}
#endregion
}
Выглядеть в редакторе кода это (свёрнутый регион) будет так:
Рис. 1. Свёрнутый регион с кодом в редакторе кода Visual Studio 2010
В конце блока #region должна присутствовать директива #endregion. Блок #region не может накладываться на блок #if. Однако блок #region можно вложить в блок #if, а блок #if – в блок #region.
#pragma ― передаёт компилятору специальные инструкции для компиляции файла, в котором она содержится. Эти инструкции должны поддерживаться компилятором. Другими словами, директиву #pragma нельзя использовать для создания пользовательских инструкций предварительной обработки. Директива состоит из двух инструкций:
#pragma warning ― позволяет включать или отключать определенные предупреждения. Например:
#pragma warning disable warning-list
#pragma warning restore warning-list
warning-list ― параметры, список номеров предупреждений с разделителями-запятыми. Нужно вводить номер без префикса «CS». Если номера предупреждений не указаны, disable отключает все предупреждения, а restore включает все предупреждения. Пример:
// pragma_warning.cs
using System;
#pragma warning disable 414, 3021
[CLSCompliant(false)]
public class C
{
int i = 1;
static void Main()
{
}
}
#pragma warning restore 3021
[CLSCompliant(false)] // CS3021
public class D
{
int i = 1;
public static void F()
{
}
}
/* Выведет (на вкладке "Список ошибок" среды разработки Visual Studio 2010):
* "D" не требуется атрибут CLSCompliant, так как сборка не имеет атрибута CLSCompliant
*/
#pragma checksum ― создание контрольных сумм файл исходного кода для помощи в отладке страниц ASP.NET. Например:
#pragma checksum "filename" "{guid}" "checksum bytes"
"filename" ― имя файла, для которого требуется отслеживание изменений и обновлений.
"{guid}" ― идентификатор GUID этого файла.
"checksum_bytes" ― шестнадцатеричное значение контрольной суммы. Должно содержать четное количество шестнадцатеричных чисел. В случае нечетного количества при компиляции будет показано предупреждение, а директива не будет обработана.
Отладчик Visual Studio 2010 использует контрольную сумму для проверки правильности исходного кода. Компилятор вычисляет контрольную сумму для файла исходного кода, затем передает результат в файл PDB базы данных программы. После этого отладчик использует PDB для сравнения с вычисленной контрольной суммой.
Это решение не работает для проектов ASP.NET, поскольку контрольная сумма вычисляется для файла исходного кода, а не для ASPX-файла. Для решения этой проблемы функция #pragma checksum обеспечивает поддержку контрольных сумм для страниц ASP.NET.
При создании проекта ASP.NET в Visual C# созданный файл исходного кода содержит контрольную сумму для ASPX-файла, из которого создается файл исходного кода. Затем компилятор записывает эти данные в файл PDB.
Если компилятор не находит директивы #pragma checksum в файле, он вычислят контрольную сумму и записывает значение в файл PDB. Пример:
// pragma_checksumg.cs
using System;
class Program
{
static void Main()
{
#pragma checksum "pragma_checksumg.cs" "{3673e4ca-6098-4ec1-890f-8fceb2a794a2}" "{012345678AB}" // Новая checksum (значения "якобы" настоящие)
}
}