Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Лекции С++.docx
Скачиваний:
4
Добавлен:
22.09.2019
Размер:
6.95 Mб
Скачать

Оператор вывода (пример)

bool T::writeTxt(ostream& ostr);

ostream&

operator<<(ostream& ostr, T& rhs)

{

rhs.writeTxt(ostr); return ostr;

}

18.02.2012

cppNewb.ru 47

Друзья

  • функция-член

    • имеет доступ к закрытой части объявления

    • находится в области видимости класса

    • должна вызываться для экземпляров класса

(имеется указатель this)

  • друг (friend-функция или friend-класс)

    • имеет доступ к закрытой части объявления

18.02.2012

cppNewb.ru 48

Friend-функция

  • указывается в объявлении класса,

другом которого она является

  • может указываться в любой секции

(public, protected, private)

18.02.2012

cppNewb.ru 49

Friend-функция (пример)

class CMatrix;

class CVector

{

friend CVec operator*(const CMatr&, const CVec&);

};

class CMatrix

{

friend CVec operator*(const CMatr&, const CVec&);

};

CVec operator*(const CMatr& lhs, const CVec& rhs)

{

//…

}

18.02.2012

cppNewb.ru 50

Использование друзей

(рекомендации)

  • друзей использовать не рекомендуется

  • реализация сильно связных концепций

  • удовлетворение обоснованных требований по оптимизации

18.02.2012

cppNewb.ru 51

Объектно-ориентированное

программирование

с использованием C++

Полевой Дмитрий Валерьевич к.т.н., доцент КИК

e-mail: oop.misis@gmail.com

Подстановка значений

  • “волшебные числа”

  • вычисления на этапе компиляции

  • подстановка значений (без выделения памяти)

#define MAX_PATH 256

или

const int MAX_PATH(256);

25.02.2012 cppNewb.ru 2

Константность (const)

  • замена препроцессора

  • строгий контроль типов

  • защита данных

  • оптимизация

25.02.2012 cppNewb.ru 3

Константность и защита данных

  • инициализация в процессе выполнения

  • изменение не предусмотрено

  • компилятор пресекает попытки потенциального изменения (проверка присваиваний)

25.02.2012 cppNewb.ru 4

Указатель (pointer)

  • тип Т* - тип “указатель на Т”

  • переменная типа Т* содержит адрес объекта типа Т

  • разыменование (косвенное обращение)

пример:

char с1 = ‘а’;

char* p = &с1; //< адрес переменной с1 char с2 = *p; //< с2 == ‘а’

25.02.2012 cppNewb.ru 5

Ноль

  • ноль (0) имеет тип int

  • константа

    • арифметический тип

    • указатель

  • NULL

    • использовать запрещено

    • макрос

25.02.2012 cppNewb.ru 6

Нулевой указатель

  • гарантируется отсутствие объектов с адресом 0

  • 0 – указатель, который ни на что не ссылается

  • разыменование нулевого указателя –

ошибка времени исполнения

25.02.2012 cppNewb.ru 7

Массив (встроенный)

  • составной пользовательский тип

  • тип T[size] – тип “массив из size

элементов типа Т”

  • элементы индексируются от 0 до size-1

  • в памяти расположены подряд

пример:

int divisors[12]; //! не инициализирован

25.02.2012 cppNewb.ru 8

Инициализация встроенного массива

  • списком инициализаторов

  • размер массива м.б. вычислен по списку инициализации

  • не указанные в списке значения инициализируются по умолчанию

  • используйте T arr[SIZE] = {0};

пример:

int ar1[] = {l, 2, 3, 4}; int ar2[32] = {l, 2};

int ar3[MAX_NUMS] = {0};

25.02.2012 cppNewb.ru 9

Указатели и массивы

  • имя массива – указатель на первый элемент

  • доступ через указатели или оператор []

пример:

p = &v[0]; //< или p = v;

v[i] == *(p + i)

25.02.2012 cppNewb.ru 10

Доступ к элементам массива

  • указатель на массив и индекс

пример:

data[i]

  • указатель на элемент массива

пример:

*(pData + i)

25.02.2012 cppNewb.ru 11

Арифметика указателей

  • сложение с целым числом

  • вычитание целого числа

  • вычитание указателей

25.02.2012 cppNewb.ru 12

Сложение и вычитание

(целых чисел)

  • “сдвиг” указателя на заданное число элементов массива

  • результат разыменования не определен, если адрес вне массива

25.02.2012 cppNewb.ru 13

Вычитание указателей

  • определено только для указателей на элементы одного массива (язык не позволяет быстро проверить)

  • число (целое) элементов массива между указателями

25.02.2012 cppNewb.ru 14

Указатель на void

  • содержит адрес объекта

  • допустимые операции

    • присвоение адреса

    • сравнение на равенство и неравенство

    • явное преобразование к указателю на другой тип

  • запрещенные операции

    • разыменование

    • арифметические операции

25.02.2012 cppNewb.ru 15

Указатель (в функциях)

  • параметр

  • возвращаемое значение

пример:

int* min(const int* pLhs, const int* pRhs)

{

// проверить != 0 для обоих аргументов

return (*pLhs < *pRhs )? pLhs : pRhs;

}

25.02.2012

cppNewb.ru 16

Указатель на константу и константный указатель

  • указатель на константную переменную

const T* p = 0;

  • константный указатель

/// д.б. инициализирован

T* const pC = &obj;

  • константный указатель на константную переменную

/// д.б. инициализирован

const T* const pC = &obj;

25.02.2012 cppNewb.ru 17

Передача и возвращение адресов (указатели и ссылки)

  • позволяет избежать накладных расходов на копирование

  • требует дополнительного контроля доступа и изменений

25.02.2012 cppNewb.ru 18

Объект, указатель или ссылка?

  • если тип не фундаментальный, используйте ссылку или указатель (избегайте лишних объектов)

  • предпочитайте ссылки

  • если объекта может не существовать,

используйте указатель

  • помните о константности

25.02.2012 cppNewb.ru 19

Память (статическая, стек, куча)

  • статическая память (при компиляции)

    • глобальные переменные

    • статические переменные

  • стек

    • параметры функций

    • локальные переменные

  • куча (heap)

    • динамическое распределение new/delete

25.02.2012

cppNewb.ru 20

Динамические объекты

  • время жизни не ограничено областью видимости переменной, а полностью определяется пользователем

  • “живут” в динамической памяти

25.02.2012 cppNewb.ru 21

Операторы работы с динамическими объектами

  • оператор new – создает объект

  • оператор delete – уничтожает объект

    • указатель, возвращенный new

    • 0 (ноль)

пример:

int* pCounter = new int; //< создадим объект

++(*pCounter);

delete pCounter; //< уничтожим объект

pCounter = 0; //< обнулим для верности

25.02.2012 cppNewb.ru 22

Динамические массивы

  • new T[SIZE]

  • delete[]

пример:

/// Cоздадим массив объектов.

int* pCounters = new int[NCOUNTERS];

*(pCounters + 5) += 1;

/// Уничтожим массив.

delete[] pCounters;

pCounters = 0; //< обнулим для верности

25.02.2012 cppNewb.ru 23

Указатель на себя

  • this – ключевое слово, указатель на текущий экземпляр

  • определен внутри нестатических методов

  • нельзя получить адрес

  • нельзя присвоить значение

  • используется неявно

25.02.2012

cppNewb.ru 24

Пример неудачный (this)

пример:

void

Point::setX(const int x)

{

}

или

this->m_x = x;

void

Point::setX(const int x)

{

(*this).m_x = x;

}

25.02.2012

cppNewb.ru 25

Пример удачный (this)

T& T::operator++()

{

// содержательная работа

return *this;

}

25.02.2012

cppNewb.ru 26

Использование this

  • использовать единообразно

  • избегать избыточности

    • использовать при необходимости,

т.е. НЕ для доступа к членам в методах

25.02.2012

cppNewb.ru 27

Константные поля

  • не изменяются после создания объекта

  • инициализируются в списке инициализации

25.02.2012

cppNewb.ru 28

Константные поля (пример)

class FixedArr

{

public:

FixedArr(int size); private:

const int m_size;

///…

};

FixedArr::FixedArr(int size)

: m_size(size)

///…

25.02.2012

cppNewb.ru 29

Константные методы

  • сохраняют логическую константность

    • не изменяют состояния полей кроме

mutable

  • могут вызываться для константных экземпляров

  • отличаются от неконстантных методов с тем же набором параметров

25.02.2012

cppNewb.ru 30

Константные методы (пример)

class FixedArr

{

}; int

public:

//…

int size() const;

//…

FixedArr::size() const

{

//…

25.02.2012

cppNewb.ru 31

Члены-ссылки

  • сильно связанные данные (классы)

  • инициализируются в списке инициализации

  • блокируют создание умолчательного конструктора

25.02.2012

cppNewb.ru 32

Ссылочные члены (поля)

class Point

{

public:

Point(Axes& axes); private:

Axes& m_axes;

///…

};

Point::Point(Axes& axes)

: m_axes(axes)

///…

25.02.2012

cppNewb.ru 33

Инвариант класса

  • “всегда” истинное логическое утверждение (члены)

  • выполняется в начале и конце метода

  • может нарушаться внутри метода

25.02.2012

cppNewb.ru 34

Локальная переменная

  • конструктор вызывается когда управление передается инструкции, содержащей объявление переменной

  • деструктор вызывается при выходе из

блока, содержащего объявление переменной

25.02.2012

cppNewb.ru 35

Умолчательный конструктор

  • конструктор без аргументов

  • генерируется автоматически, если нет объявления других конструкторов

  • вызывается

    • создание переменной без использования инициализаторов

    • создание элемента массива

25.02.2012

cppNewb.ru 36

Копирование объектов

  • инициализация через копирование

  • присваивание

  • передача аргументов и возврат значений

  • умолчательно является созданием точной бинарной копии

25.02.2012

cppNewb.ru 37

Класс с указателями (пример)

class String

{

public: String()

: m_pStr(new char[SIZE_DEF])

{}

~String()

{

delete[] m_pStr;

}

private:

char m_pStr;

};

25.02.2012

cppNewb.ru 38

Проблемы копирования (пример)

CString str1;

/// Копирующая инициализация – проблема!

CString

str2 =

str1;

CString

str3;

/// Копирующее присваивание – проблема!

str3 = str1;

25.02.2012

cppNewb.ru 39

Копирование и управление ресурсами

  • почленное копирование неправильно для классов, реализующих управление ресурсами (конструктор/деструктор)

  • необходимо использовать пользовательский конструктор копирования и оператор присваивания

25.02.2012

cppNewb.ru 40

Конструктор копирования

T::T(const T&)

  • генерируется автоматически, если не определен пользователем

  • м.б. запрещен, определением в private

25.02.2012

cppNewb.ru 41

Конструктор копирования

(пример)

String::String(const String& copy)

: m_pStr(new char[copy.size()])

, m_len(copy.len)

{

memcpy(m_pStr, copy.m_pStr, sizeof(*m_pStr) * size());

}

25.02.2012

cppNewb.ru 42

Оператор присваивания

T& T::operator=(const T&)

  • генерируется автоматически, если не определен пользователем

  • м.б. запрещен, определением в private

25.02.2012

cppNewb.ru 43

Схема присваивания (простая)

  • защита от присваивания самому себе

  • удаление старых элементов

  • создание и инициализация

(копирование) новых элементов

  • существует другая схема (безопасная при исключениях)

25.02.2012

cppNewb.ru 44

Оператор присваивания (пример)

T& T::operator=(const T& copy)

{

// защита от присваивания самому себе

if (this != &copy)

{

// копирование

}

return *this;

}

25.02.2012

cppNewb.ru 45

Инициализация и присваивание

  • копирующий конструктор

    • инициализирует неинициализированную память

  • копирующее присваивание

    • должно обеспечивать правильную работу с уже созданными объектами

  • избегайте ошибок при попытке уменьшения объема кода

25.02.2012

cppNewb.ru 46

Ошибка генерации автоматического копирования

  • если нестатический член является

    • ссылкой

    • константой

    • определяемым пользователем типом, не имеющим копирующего оператора присваивания

25.02.2012

cppNewb.ru 47

Структура (struct)

  • составной пользовательский тип

  • определяет набор (почти)

произвольных типов

  • именованный доступ

25.02.2012 cppNewb.ru 48

POD типы

  • Plain Old Data

  • объекты можно копировать как фрагменты памяти

25.02.2012

cppNewb.ru 49

Пример структур

пример:

struct Address

{

char[256] m_name; unsigned int m_zip;

};

Adress companyAddress; //! не инициализирован

Adress myAddress = {“D.V. Polevoy”, 156987};

25.02.2012 cppNewb.ru 50

Доступ к членам структур

  • аналогично классам

  • . – оператор доступа к члену

  • -> – оператор разыменования члена структуры (для указателя на структуру)

25.02.2012 cppNewb.ru 51

Перечисление (enum)

  • пользовательский тип

  • может иметь собственное имя

  • определяет набор определяемых пользователем константных значений

  • приводится к целому в выражениях

25.02.2012 cppNewb.ru 52

Примеры перечислений

enum KeyWord

{

ASM, AUTO, BREAK

};

KeyWord word(ASM);

enum Status

{

OFF, ON,

DISABLE = 255

}

25.02.2012 cppNewb.ru 53

Объектно-ориентированное

программирование

с использованием C++

Полевой Дмитрий Валерьевич к.т.н., доцент КиК

e-mail: oop.misis@gmail.com

Базовые принципы ООП

0. абстракция

  1. инкапсуляция

  1. наследование

  1. полиморфизм

03.03.2012

www.cppNewb.ru 2

Повторное использование кода

  • уменьшение “стоимости” создания и поддержки ПО

    • разработка

    • отладка и тестирование

    • сопровождение

    • модификация

  • эффекты “массовости”

03.03.2012

www.cppNewb.ru 3

Реализация повторного использования кода

  • модульность – использование готовых компонент (классы, библиотеки)

  • создание новых классов на основе существующих

    • инстанциирование (шаблоны)

    • наследование

03.03.2012

www.cppNewb.ru 4

Проблема повторного использования алгоритмов

  • один и тот же алгоритм может обрабатывать данные разных типов

пример:

int

minimum(int lhs, int rhs)

{

return (lhs < rhs) ? lhs : rhs;

}

03.03.2012

www.cppNewb.ru 5

Как использовать алгоритм с разными типами?

  • copy-past

    • размножение “одинаковых сущностей” и внесение новых ошибок

    • усложнение поддержки кода

  • макрос

    • усложнение отладки и поддержки

пример:

#define min(ls, rs) ((ls < rs) ? ls : rs)

03.03.2012

www.cppNewb.ru 6

Как использовать алгоритм с разными типами?

  • реализовать шаблонный код

пример: template<class T> T

min(const T& lhs, const T& rhs)

{

return (lhs < rhs) ? lhs : rhs;

}

03.03.2012

www.cppNewb.ru 7

Ключевые слова

  • template

    • описание параметризации шаблонна

  • class и typename

    • именование параметра

пример:

template<class T>

или

template<typename T>

03.03.2012

www.cppNewb.ru 8

Структура шаблонного кода

template<“параметры”> “объявление”

template<“параметры”>

“определение”

03.03.2012

www.cppNewb.ru 9

Шаблон (template)

  • в определении (класса или функции) используется один или несколько неизвестных (именованных) типов

  • типы должны быть известны в момент компиляции программы

03.03.2012

www.cppNewb.ru 10

Преимущества шаблонов

  • автоматическая генерация кода

  • оптимизация программ

  • использование типа при определении

функции или класса

  • зависит только от тех параметров типа,

которые использует

03.03.2012

www.cppNewb.ru 11

Инстанциирование шаблона

  • генерация объявления функции (класса) по шаблону функции (класса) и аргументам шаблона

  • осуществляется компилятором на этапе компиляции

  • сгенерированный код подчиняется стандартным правилам

03.03.2012

www.cppNewb.ru 12

Шаблонная функция

  • определяется шаблоном и набором параметров

03.03.2012

www.cppNewb.ru 13

Шаблонный класс (тип)

  • определяется шаблоном и набором параметров

  • при использовании одного набора

параметров генерируется один и тот же тип (эквивалентные типы)

03.03.2012

www.cppNewb.ru 14

Шаблонный класс (пример)

template<class T> class CStack

{

public: CStack();

T getTop(); private:

T* m_pData;

};

03.03.2012

www.cppNewb.ru 15

Параметры шаблонов

  • тип (типизированный параметр)

  • константа времени компиляции

(нетипизированный параметр)

  • другие шаблоны

  • м.б. несколько

03.03.2012

www.cppNewb.ru 16

Шаблоны членов и методов класса

  • шаблон класса может иметь шаблонные члены и шаблонные методы

  • нешаблонный класс может иметь шаблонные методы

03.03.2012

www.cppNewb.ru 17

Нетипизированный параметр

  • известное на стадии компиляции целочисленное значение (литерал или выражение)

  • адрес объекта

  • функция с внешней компоновкой

  • неперегружаемый указатель на член

03.03.2012

www.cppNewb.ru 18

Нетипизированный параметр

(пример) template<class T, size_t N> class CArr

{

… private:

T m_data[N];

};

CArr<int, 128> members;

03.03.2012

www.cppNewb.ru 19

Типизированный параметр

  • фундаментальный тип

  • пользовательский тип

  • шаблонный тип

03.03.2012

www.cppNewb.ru 20

Типизированный параметр

(пример) template<class T, size_t N> class CArr

{

… private:

T m_data[N];

};

CArr<int, 128> members;

03.03.2012

www.cppNewb.ru 21

Проверка

  • при определении шаблона

    • ошибки, которые можно обнаружить вне зависимости от конкретного набора аргументов

  • при инстанциировании шаблона

    • ошибки, которые имеют отношение к использованию параметров

03.03.2012

www.cppNewb.ru 22

Слабая типизация

  • тип обеспечивает интерфейс,

ожидаемый шаблоном

  • требуется доступность вызываемых функций для типов, параметризующих шаблоны

03.03.2012

www.cppNewb.ru 23

Слабая типизация (пример)

template<typename T> T

min(const T& lhs, const T& rhs)

{

return (lhs < rhs) ? lhs : rhs;

}

03.03.2012

www.cppNewb.ru 24

Параметры шаблона функции

  • могут быть выведены компилятором, если однозначно определяются списком аргументов

  • могут быть указаны явно

пример:

int minVal(minimum<int>(a, b));

03.03.2012

www.cppNewb.ru 25

Параметры шаблона класса

  • должны указываться явно, т.к. никогда не выводятся

пример:

vector<int> marks;

  • для выведения списка параметров м.б.

использована генерирующая

экземпляры шаблонного класса функция

пример:

make_pair(a, b)

03.03.2012

www.cppNewb.ru 26

Автоматическая генерация экземпляров шаблонного класса

template <class T1, class T2> struct pair ;

template <class T1,class T2> pair<T1,T2>

make_pair(const T1& x, const T2& y)

{

return pair<T1, T2>(x, y);

}

03.03.2012

www.cppNewb.ru 27

Перегрузка функций

  • можно объявлять

    • несколько шаблонов с одним именем

    • комбинацию шаблонов и обычных функций с одним именем

  • выбор функции

    • явный квалификатор (параметры шаблона)

    • разрешение вызова

03.03.2012

www.cppNewb.ru 28

Перегрузка

функций

(пример)

template<typename T sqrt(T);

T>

template<typename

T>

complex<T> sqrt(const complex<T>&);

double sqrt(double);

03.03.2012

www.cppNewb.ru 29