230 likes | 439 Views
Основы информатики Классы. Заикин Олег Сергеевич zaikin.icc@gmail.com. Объектно-ориентированное программирование. Инкапсуляция - скрытие деталей реализации, обеспечение доступности главного путем помещения всего мешающего, второстепенного в некую условную капсулу (чёрный ящик ) .
E N D
Основы информатикиКлассы Заикин Олег Сергеевич zaikin.icc@gmail.com
Объектно-ориентированное программирование • Инкапсуляция - скрытие деталей реализации, обеспечение доступности главного путем помещения всего мешающего, второстепенного в некую условную капсулу (чёрный ящик). • Наследование позволяет создавать иерархию объектов, в которой объекты-потомки наследуют все свойства своих предков. Свойства при наследовании повторно не описываются. Кроме унаследованных, потомок обладает собственными свойствами. Объект в C++ может иметь сколько угодно потомкови предков. • Полиморфизм - возможность определения единого по имени действия, применимого ко всем объектам иерархии, причем каждый объект реализует это действие собственным способом.
Класс Объектно-ориентированное программирование основано на понятии класса. Класс – абстрактный тип данных в объектно-ориентированном программировании. Объект – экземпляр класса. Класс задает формат объекта. Класс – абстракция, которая реально не существует, пока не будет создан объект этого класса.
Класс Объявляя класс, Вы задаете данные и код, который выполняется над данными. Простой класс может содержать только данные или только код, но обычно содержится и то и другое. Класс в итоге определяется как список своих членов, а именно полей (свойств) и методов/функций/процедур.
Класс • Объявление класса начинается с ключевого слова classи синтаксически подобно объявлению структуры. • По умолчанию члены класса являются закрытыми (private), т.е. к ним могут получить доступ только функции этого же класса. Никакие другие части программы этого не могут. Это одно из проявлений инкапсуляции – можно управлять доступом к определенным элементам данных. Для открытости нужно использовать ключевое слово public. • class <имя> { • private: • <описание скрытых извне членов класса> • public: • <описаниедоступных извне членов класса> • };
Поля класса • Поля класса: • могут иметь любой тип, кроме типа этого же класса (но могут быть указателями или ссылками на этот класс); • могут быть описаны с модификатором const. • Инициализация полей при описании не допускается. • Тело класса определяет отдельную область видимости. Наличие в двух разных классах членов с одинаковыми именами – не ошибка, эти имена относятся к разным областям видимости.
Функции класса Функции (методы) класса объявляются в его теле. Функции класса отличается от обычных функций следующим: функции класса имеют право доступа как к открытым, так и к закрытым членам класса, тогда как обычным функциям доступны лишь открытые. Конечно, функции одного класса, как правило, не имеют доступа к данным другого класса.
Пример класса Пример. Класс очередь (queue) class queue { int q[100]; int sloc, rloc; void init(); void qput(int i); int qget(); }; Почему класс queue бесполезен? Эквивалентно class queue { private: int q[100]; int sloc, rloc; void init(); void qput(int i); int qget(); };
Класс class queue { int q[100]; int sloc, rloc; public: void init(); void qput(int i); int qget(); }; Теперь к функциям init(), qput() и qget() доступ открытый. Хотя бы к одной функции класса должен быть открытый доступ, иначе невозможно что-либо сделать с полями класса.
Класс После создания объект имеет собственную копию данных, которые составляют класс. Объект занимает определенную область памяти. Чтобы получить доступ к открытому члену класса используется оператор «точка», как и при работе со структурами. К закрытым членам класса так обратиться нельзя. Пример queue Q1, Q2; // объявление двух объектов класса queue Q1.init(); // вызов открытой функции Q1.sloc = 3; // ошибкакомпиляции - попытка обращения к закрытому члену класса.
Класс В объявлении класса содержатся только прототипы функций. Чтобы реализовать функцию, необходимо указать к какому классу она принадлежит.Для этого перед именем функции нужно поставить имя класса и “::”. “::” - оператор разрешения области видимости, он квалифицирует имя члена класса вместе с именем его класса. Пример void queue :: qput(int i) { if (sloc == 100) { cout << “Очередь заполнена”<< endl; return; } q[sloc++] = i; }
Класс Различные классы могут использовать одинаковые имена своих членов. С помощью оператора “::” компилятор определит, к какому классу он относится. Для вызова из функции класса другой функции этого же класса оператор “.” не требуется. Аналогично для обращения к полям класса. Пример void queue :: init() { rloc = sloc = 0;// указывать область видимости не нужно }
Класс Обычно описание класса помещают в заголовочный файл (расширение *.h), а реализацию функций класса – в файл c расширением *.cpp.Называться файлы должны одинаково. Файл queue.h class queue { int sloc, rloc; public: void init(int i); }; Файл queue.cpp #include “queue.h”; void queue :: init() { rloc = sloc = 0; }
Закрытые элементы Если rloc и sloc будут public, к чему это может привести? // функция возвращает текущее количество элементов в очереди int queue :: size() { return sloc - rloc; }
Присваивание объектов Если есть два объекта одного класса, то один можно присвоить другому. По умолчанию данные поразрядно копируются, в том числе закрытые. queue Q1. Q2; Q1.init(); // Q1.rloc == 0, Q2.rloc неопределен Q2 = Q1; // Q1.rloc == 0, Q2.rloc == 0 Если в классе есть указатель, что произойдет при копировании объектов?
Присваивание объектов class myclass { int *a; } ; myclass x, y; x.a = new int[2]; y = x; Если в классе есть переменная-указатель, что произойдет при копировании объектов?
Конструктор • Конструктор – функция, которая автоматически вызывается при создании объекта. Имя конструктора совпадает с именем класса. • Используется для инициализации части данных. • Если программист не указал ни одного конструктора, компилятор создает его автоматически. Такой конструктор вызывает конструкторы по умолчанию для полей класса и конструкторы по умолчанию базовых классов. • Например для класса queue при инициализации переменным rloc и sloc нужно присвоить нулевые значения. • В рассмотренном ранее примере инициализация выполняется в функции init().
Конструктор Пример class queue { int q[100]; int sloc, rloc; public: queue(); // конструктор void qput(int i); int qget(); }; queue :: queue() { sloc = rloc = 0; } queue Q1, Q2; // создано 2 объекта, у каждого вызван конструктор
Деструктор Деструктор – функция, которая вызывается при разрушении объекта. Нужен для освобождения ранее выделенной для объекта памяти или других действий при разрушении объекта. Имя деструктора –это имя конструктора, перед которым стоит символ ~ class queue { int q[100]; int sloc, rloc; public: queue(); // конструктор ~queue(); // деструктор void qput(int i); int qget(); };
Деструктор • Деструктор вызывается автоматически, когда объект выходит из области видимости: • для локальных объектов — при выходе из блока, в котором они объявлены; • для глобальных — как часть процедуры выхода из main; • для объектов, заданных через указатели, деструктор вызывается неявно при использовании операции delete.
Деструктор • Деструктор можно вызвать явным образом путем указания полностью уточненного имени, например: • queue *q; ... • q -> ~queue(); • Деструктор: • не имеет аргументов и возвращаемого значения; • Если деструктор явным образом не определен, компилятор автоматически создает пустой деструктор.