
- •1.Объявление и определение класса.
- •3. Дружественные функции.
- •4. Пеpегpузка опеpаций ( синтаксис operator)
- •5. Статические компоненты класса.
- •7. Иерархия классов ( последовательность работы конструкторов и деструкторов )
- •8. Доступ к наследуемым компонентам
- •9. Виртуальные функции (когда применяются, форма вызова)
- •10 . Шаблоны ( пример template)
- •15 Преобразование типов данных.
- •17 Ввод-вывод в файл. Сохранение объектов в файле.
- •18 Обработка исключений (блоки try, throw, catch)
- •Примеры обработки исключительных ситуаций
- •20. Паттерны и их классификация. Принцип классификации паттернов проектирования
- •Паттерны проектирования классов/обьектов
- •21. Абстрактная фабрика.
- •22. Классификация типов данных. Система типов
- •Oбщий взгляд
- •Класс String
- •Объявление строк. Конструкторы класса string
- •Операции над строками
- •Цикл foreach
- •Наследование
- •Добавление полей потомком
- •Конструкторы родителей и потомков
- •Интерфейсы
- •Две стратегии реализации интерфейса
- •Преобразование к классу интерфейса
1.Объявление и определение класса.
Класс в С++ аналогичен понятию типа. Программист должен определить тип и длину полей и функции, работающие с этими полями (такие функции называются методами). Класс является фундаментальным понятием С++.
Отличительной особенностью С++ является то обстоятельство, что имеется возможность управлять доступом к данным класса, в частности, введение такого порядка, при котором доступ к полям конкретного класса имеют только его методы. Объединение данных и методов работы с ними в одну языковую конструкцию, а также управление доступом к данным называется инкапсуляцией. Ниже приведен пример класса комплексных чисел.
class Complex{ // 1 double re, im; // 2 public: // 3 Complex(double r, double i){re=r; im=i;} // 4 Complex(){re=0; im=0;} // 5 double getR(){ return re;} // 6 double getI(){ return im;} // 7 void setC(double a, double b){re=a; im=b;} // 8 }; // 9 void main(){ Complex m1(4,6), m2, m3[6]; // 10 m2.setC(5, 8); // 11 cout<<m2.getR()<<m2.getI()<<endl; // 12 }
Кратко рассмотрим составляющие программы. Со строки 1 начинается определение класса. В строке 2 объявлены два поля – данные класса. Ключевое слово public в строке 3 определяет соответствующий доступ к полям класса. В строках 4 и 5 приведены конструкторы класса – функции, создающие поля класса. В строках 6 – 8 записаны методы: первые два возвращают значения реальной и мнимой частей комплексного числа соответственно, третий устанавливает их значения. Девятой строкой заканчивается определение класса. В 10 строке объявляются 3 объекта (экземпляра) класса: переменные m1 и m2 (m1 инициализируется при объявлении) и массив m3. Оператор в 11 строке присваивает полям переменной m2 соответствующие значения, в 12 строке производится вывод этих значений на экран.
Определение класса имеет следующий вид:
тип_класса имя_класса { поля, методы };
Тип класса может быть задан одним из 3-х атрибутов: class, struct, union. Имя класса становится идентификатором нового типа данных. Поля определяются с помощью базовых типов, методы записываются как обычные функции. Поля и методы, включенные в класс, называются его компонентами. Совокупность методов далее будем называть интерфейсом класса.
Если тела функций включены в определение класса, то такие функции считаются встроенными по умолчанию. В случае сложных функций в определении класса записываются только их прототипы; тела приводятся вне класса с указанием их полного имени. Полное имя компоненты класса записывается следующим образом:
[тип] имя_класса:: имя_компоненты,
где символ :: называется оператором принадлежности. Если перед этим оператором нет имени класса, то задаваемое имя определяется как глобальное, известное за пределами классов.
В программе наряду с определением класса допускается его объявление вида:
тип_класса имя_класса;
Примеры
class X; // Объявление класса Х
class Y { // Определение класса Y
X m1;
...
}
class X{ // Определение класса Х
...
}
Один класс можно объявить в другом классе. Первый при этом называется вложенным.
2 Конструкторы и деструкторы ( типы конструкторов и деструкторов)
Конструктор – функция, создающая поля класса и, возможно, их инициализирующая. Приведем пример достаточно сложного класса String.
class String{ // 1 char *charPtr; // 2 int length; // 3 public: // 4 String(int size=80); // 5 String(char *text); // 6 String(String& Other_String); // 7 ~String(){delete charPtr;}; // 8 int GetLen(void); // 9 void Show(void); //10 }; String::String (int size){ length=size; charPtr=new char[length + 1]; *charPtr =‘\0’; } String::String(char *text) { length=strlen(text); char_ptr=new char [length+1]; strcpy(charPtr, text); } String::String(String& Other_String) { length=Other_String.length; char_ptr=new char[length+1]; strcpy(charPtr, Other_String.charPtr); }
Первый конструктор класса String (строка 5) создает строку с заданной длиной (по умолчанию 80). Второй конструктор создает поле для символьной строки и инициализирует его текстом, передаваемым в качестве аргумента. Начальное значение для поля класса здесь задается как аргумент конструктора. Наряду с этим начальные значения могут задаваться в виде списка инициализации, который отделяется от списка аргументов конструктора двоеточием. Второй способ инициализации иногда предпочтительнее, т. к. в этот список можно включать компоненты другого класса. Третий конструктор (строка 7) копирует уже имеющуюся строку, во вновь создаваемую, и называется конструктором копирования.
Пример использования всех трех конструкторов следует ниже:
void main() { String Astring(" Инкапсуляция"); String Bstring(Astring); String Cstring(25); . . . }
В результате выполнения программы получаем три объекта: 2 строки с одинаковым содержимым и одну пустую строку длиной 25 символов.
Перечислим основные свойства и правила использования конструкторов:
конструктор имеет то же имя, что и класс, в котором он объявляется;
конструктор не имеет типа возвращаемого значения;
конструктор может иметь аргументы, заданные по умолчанию; эти аргументы не перечисляются при вызове конструктора;
если конструктор не задан в программе, то компилятор автоматически создает конструктор без аргументов;
конструктор вызывается автоматически только при создании объекта;
конструктор класса X может иметь аргумент типа X& (ссылку на объект типа X), но не аргумент типа X.
конструктор, заданный в виде X::X(X&), называется конструктором копирования; он подразумевает использование свободной памяти.
Деструктор разрушает поля класса; его можно узнать по символу ~. Деструктор не имеет аргументов и не возвращает значения. В классе может быть только один деструктор. Если деструктор не задан в программе, то он автоматически генерируется компилятором. Деструктор автоматически вызывается при разрушении объекта за исключением случая, когда массив объектов создается оператором new. В последнем случае для разрушения объектов должен быть использован оператор delete для каждого элемента массива. (В классах Complex и String деструкторы вызываются автоматически).