- •1. Введение в ооп
- •1.1. Этапы развития технологий программирования
- •1.2. Введение в ооп
- •2. Понятие класса и объекта класса. Инкапсуляция в c#
- •2.1. Понятие класса и объекта класса. Создание объектов. Данные и методы класса
- •2.2. Передача параметров в методы класса
- •2.3. Конструкторы и деструкторы
- •2.4. Инкапсуляция в c#
- •3. Индексаторы и свойства
- •3.1. Индексаторы
- •3.2. Свойства
- •4. Наследование в c#
- •5. Полиморфизм в c#. Интерфейсы
- •5.1. Виртуальные методы и их переопределение
- •5.2. Применение абстрактных классов
- •5.3. Интерфейсы
- •6. Система типов языка c#
- •7. Структуры и перечисления
- •7.2. Тип структур
- •8. Операторы и управляющие конструкции языка c#
- •8.1. Арифметические операторы
- •8.2. Операторы отношения и логические операторы
- •8.3. Оператор присваивания
- •8.4. Оператор ?
- •8.5. Управляющие операторы
- •9. Массивы и строки
- •9.1. Массивы в c#
- •9.1.1. Одномерные массивы
- •9.1.2. Многомерные массивы
- •9.1.3. Ступенчатые массивы
- •9.2. Строки
- •9.2.1. Постоянство строк
- •10. Платформа .Net. Основные понятия и принципы работы
- •11. Пространства имен. Сборки
- •11.1. Пространства имён
- •11.2. Сборки
- •12. Время жизни переменных и область видимости переменных. Оператор new и сборка мусора
- •12.2. Финализация объектов
- •12.3. Создание высвобождаемых объектов
- •13. Исключения. Генерация и обработка
- •13.1. Основы обработки исключительных ситуаций
- •13.2. Применение пары ключевых слов try и catch
- •13.3. Генерирование исключений вручную
- •13.4. Использование блока finally
- •13.5. Класс Exception и получение производных классов
- •13.6. Ключевые слова checked и unchecked
- •14. Обобщения (шаблоны) и их применение в языке c#
- •15. Основные классы коллекций объектов
- •15.1. Интерфейсы необобщенных коллекций
- •15.1.1. Интерфейс iCollection
- •15.1.2. Интерфейс iList
- •15.1.3. Интерфейс iDictionary
- •16. Использование linq для работы с коллекциями
- •16.1. Простой запрос
- •16.2. Общая форма запроса
- •16.3. Сортировка результатов запроса с помощью оператора orderby
- •16.4 Операторы group, into, let и join
- •16.5. Методы запроса
- •16.6. Формирование запроса с помощью методов запроса
- •Заключение
- •Оглавление
- •1. Введение в ооп 3
- •1.1. Этапы развития технологий программирования 3
- •1.2. Введение в ооп 11
- •394026 Воронеж, Московский просп., 14
6. Система типов языка c#
Как и в любом языке программирования, в С# поставляется собственный набор основных типов данных, которые должны применяться для представления локальных переменных, переменных экземпляра, возвращаемых значений и входных параметров. Однако в отличие от других языков программирования, в С# эти ключевые слова представляют собой нечто большее, чем просто распознаваемые компилятором лексемы. Они, по сути, представляют собой сокращенные варианты обозначения полноценных типов из пространства имен System. В табл. 3 0перечислены эти системные типы данных вместе с охватываемыми ими диапазонами значений, соответствующими ключевыми словами на С# и сведениями о том, отвечают ли они требованиям общеязыковой спецификации CLS (Common Language Specification).
Таблица 3
Системные типы данных в С#
Cокращенный вариант обозначения в С# |
Отвечает ли требованиям CLS |
Системный тип |
Диапазон значений |
Описание |
bool |
Да |
System.Boolean |
true или false |
Представляет признак истиности или ложности |
sbyte |
Нет |
System.SByte |
от -127 до 128 |
8-битное число со знаком |
byte |
Да |
System.Byte |
от 0 до 255 |
8-битное число без знака |
short |
Да |
System.Int16 |
от -32 768 до 32767 |
16-битное число со знаком |
ushort |
Нет |
System.UInt16 |
от 0 до 65 535 |
16-битное число без знака |
int |
Да |
System.Int32 |
от - 2 147 483 648 до 2 147 483 647 |
32-битное число со знаком |
uint |
Нет |
System.UInt32 |
от 0 до 4 294 967 295 |
32-битное число без знака |
long |
Да |
System.Int64 |
от -9 223 372 036 854 775 808 до 9 223 372 036 854 775 807 |
64-битное число со знаком |
ulong |
Нет |
System.UInt64 |
от 0 до 18 446 744 073 709 551 615 |
64-битное число без знака |
char |
Да |
System.Char |
от U+0000 до U+ffff |
Одиночный 16-битный символ Unicode |
float |
Да |
System.Single |
от +1,5×10-45 до 3,4×1038 |
32-битное число с плавающей точкой |
double |
Да |
System.Double |
от 5,0×10-324 до 1,7×10308 |
64-битное число с плавающей точкой |
decimal |
Да |
System.Decimal |
от ±1,0×10e-28 до ±7,9×1028 |
96-битное число с плавающей точкой |
string |
Да |
System.String |
Ограничивается объемом системной памяти |
Представляет ряд символов в формате Unicode |
object |
Да |
System.Object |
Позволяет сохранять любой тип в объектной переменной |
Служит базовым классом для всех типов в мире .NET |
Интересно отметить то, что даже элементарные типы данных в .NET имеют вид иерархии классов. Типы, которые находятся в самом верху иерархии, обеспечивают некоторое поведение по умолчанию, которое передается унаследованным от них типам. На рис. 1 схематично показаны отношения между ключевыми системными типами.
Р ис. 1. Иерархия классов системных типов
Обратите внимание, что каждый из этих типов в конечном итоге наследуется от класса System.Object, в котором содержится набор методов (таких как ToString (), Equals () и GetHashCode ()), являющихся общими для всех поставляемых в библиотеках базовых классов .NET типов.
В С# имеются две общие категории встроенных типов данных: типы значений и ссылочные типы. Они отличаются по содержимому переменной. Если переменная относится к типу значения, то она содержит само значение, например 3,1416 или 212. А если переменная относится к ссылочному типу, то она содержит ссылку на значение. Наиболее распространенным примером использования ссылочного типа является класс.
Каждый из числовых типов, такой как short или int. отображается на соответствующую структуру в пространстве имен System. Структуры представляют собой типы значений, которые размещаются в стеке. Типы string и object, с другой стороны, являются ссылочными типами, а это значит, что данные, сохраняемые в переменных такого типа, размещаются в управляемой куче.
Стек — это структура данных, которая сохраняет элементы по принципу: первым пришел, последним ушел. Стек относится к области памяти, поддерживаемой процессором, в которой сохраняются локальные переменные. Доступ к стеку во много раз быстрее, чем к общей области памяти, поэтому использование стека для хранения данных ускоряет работу вашей программы. В С# размерные типы (например, целые числа) располагаются в стеке: для их значений зарезервирована область в стеке, и доступ к ней осуществляется по названию переменной.
Ссылочные типы (например, объекты) располагаются в куче. Куча — это оперативная память компьютера. Доступ к ней осуществляется медленнее, чем к стеку. Когда объект располагается в куче, то переменная хранит лишь адрес объекта. Этот адрес хранится в стеке. По адресу программа имеет доступ к самому объекту, все данные которого сохраняются в общем куске памяти (куче).
Важно отметить, что многие из числовых типов данных унаследованы от класса System.ValueType. Потомки ValueType автоматически размещаются в стеке и потому обладают очень предсказуемым временем жизни и являются довольно эффективными. Типы, у которых в цепочке наследования не присутствует класс System.ValueType (вроде System.Type, System.String, System.Array, System.Exception и System. Delegate), в стеке не размещаются, а попадают в кучу и подвергаются автоматической сборке мусора.
Роль класса System.ValueType заключается в гарантировании размещения производного типа (например, любой структуры) в стеке, а не в куче с автоматически производимой сборкой мусора. Данные, размещаемые в стеке, могут создаваться и уничтожаться очень быстро, поскольку срок их жизни зависит только от контекста, в котором они определены. За данными, размещаемыми в куче, наблюдает сборщик мусора .NET, и время их существования зависит от целого ряда различных факторов.
С функциональной точки зрения единственной задачей System.ValueType является переопределение виртуальных методов, объявленных в System.Object, так, чтобы в них использовалась семантика, основанная на значениях, а не на ссылках. Под переопределением понимается изменение реализации виртуального (или, что тоже возможно, абстрактного) метода, определенного внутри базового класса. Базовым классом для ValueType является System.Object. В действительности методы экземпляра, определенные в System.ValueType, идентичны тем, что определены в System.Object:
// Структуры и перечисления неявным образом // расширяют возможности System.ValueType. public abstract class ValueType : object { public virtual bool Equals(object obj ) ; public virtual int GetHashCode (); public Type GetType() ; public virtual string ToString(); }
Из-за того, что в типах значения используется семантика, основанная на значениях, время жизни структуры (которая включает все числовые типы данных, наподобие int, float и т.д., а также любое перечисление или специальную структуру) получается очень предсказуемым. При выходе переменной типа структуры за пределы контекста, в котором она определялась, она сразу же удаляется из памяти.
// Локальные структуры извлекаются из стека // после завершения метода. static void LocalValueTypes () { //В действительности int представляет // собой структуру System.Int32. int i = 0; //В действительности Point представляет // собой тип структуры. Point p = new Point () ; } // Здесь i и р изымаются из стека.