- •Введение в перегрузку операций
- •Операции, как функции
- •Использование перегруженных операций
- •Ограничения в перегрузке операций
- •Перегрузка операций через дружественные функции
- •Перегрузка операций через дружественные функции
- •Int main () {
- •I have 16 dollars.
- •Int m_dollars;
- •Int getDollars () const {return m_dollars;}
- •Int main () {
- •Дружественные функции могут быть определены внутри класса
- •Int m_dollars;
- •Int getDollars () const {return m_dollars;}
- •Int main () {
- •Перегрузка операций с операндами разных типов
- •Int m_dollars;
- •Int getDollars () {return m_dollars;}
- •Int main () {
- •Values (int min, int max) {
- •Int getMin () {return m_min;}
- •Int getMax () {return m_max;}
- •Int main () {
- •Int main () {
- •Int main () {
- •Перегрузка операций через обычные функции
- •Int m_dollars;
- •Int getDollars () const {return m_dollars;}
- •Int main () {
- •Int m_dollars;
- •Int getDollars () const {return m_dollars;}
- •Int main () {
- •Int m_dollars;
- •Int getDollars () const {return m_dollars;}
- •Int main () {
- •Перегрузка операций ввода и вывода
- •Void print () {
- •Int main () {
- •Int main () {
- •Int main () {
- •Int main () {
- •Int main () {
- •Int m_numerator;
- •Int m_denominator;
- •Void reduce () {
- •Void print () {
- •Перегрузка операций через методы классов
- •Int m_dollars;
- •Int getDollars () { return m_dollars; }
- •Int main () {
- •Int m_dollars;
- •Int getDollars () {return m_dollars;}
- •Int main (){
- •Не всё может быть перегружено через дружественные функции
- •Не всё может быть перегружено через методы класса
- •Int main (){
- •Какой способ перегрузки и когда следует использовать?
- •Int m_dollars;
- •Int getDollars () const {return m_dollars;}
- •Int main () {
- •If (!isHappy)
- •Int main () {
- •If (!something)
- •Перегрузка операций сравнения
- •Int main () {
- •Int m_dollars;
- •Int main () {
- •Перегрузка операторов инкремента и декремента
- •Int m_number;
- •Int main () {
- •Перегрузка операций инкремента и декремента версии постфикс
- •Int m_number;
- •Int main () {
- •Перегрузка операции индексации []
- •Почему оператор индексации [] использует возврат по ссылке?
- •Использование оператора индексации с константными объектами класса
- •Int& operator[] (const int index);
- •Int main (){
- •IntArray array;
- •Проверка ошибок
- •Int m_array[10];
- •Int& operator [] (const int index);
- •Int& IntArray::operator[] (const int index) {
- •Указатели на объекты и перегруженный оператор []
- •Передаваемый аргумент не обязательно должен быть целым числом
- •Void operator [] (std::string index);
- •Void Something::operator [] (std::string index){
- •Int main () {
- •Перегрузка операции ()
- •Int main () {
- •Void operator() ();
- •Void Matrix::operator()() {
- •Int main() {
- •Перегрузка операций преобразования типов данных
- •Int m_dollars;
- •Int getDollars () { return m_dollars; }
- •Int main () {
Int main () {
Number number (7);
std::cout << number;
std::cout << ++number;
std::cout << ++number;
std::cout << --number;
std::cout << --number;
return 0;}
Здесь класс Number содержит число от 0 до 8. Мы перегрузили операторы инкремента/декремента таким образом, чтобы они увеличивали/уменьшали m_number в соответствии с заданным диапазоном (если выполняется инкремент и m_number равно 8, то сбрасываем значение m_number на 0; если выполняется декремент и m_number равно 0, то присваиваем значение 8 переменной m_number).
Результат выполнения программы:
78087
Обратите внимание, мы возвращаем разыменованный скрытый указатель *this т.е. текущий объект класса Number в функциях перегрузки операций.
Перегрузка операций инкремента и декремента версии постфикс
Обычно перегрузка функций осуществляется, если они имеют одно и то же имя, но разное количество и типы параметров (детально о перегрузке функций читайте в ранних лекциях).
Рассмотрим случай с функциями перегрузки операций инкремента/декремента версий префикс/постфикс.
Обе имеют одно и то же имя (например, operator++), унарные и принимают один параметр одного и того же типа данных. Как же тогда их различить при перегрузке?
Дело в том, что язык C++ использует фиктивную переменную (или «фиктивный параметр») для операторов версии постфикс.
Этот фиктивный целочисленный параметр используется только с одной целью: отличить версию постфиксную операций инкремента/декремента от версии префиксной.
Выполним перегрузку операций инкремента/декремента версии префикс и постфикс в одном классе:
#include <iostream>
class Number {
private:
Int m_number;
public:
Number (int number=0)
: m_number(number) { }
Number& operator++(); // версия префикс
Number& operator--(); // версия префикс
Number operator++(int); // версия постфикс
Number operator--(int); // версия постфикс
friend std::ostream& operator<< (std::ostream &out, const Number &n);
};
Number& Number::operator++ () {
// Если значением переменной m_number является 8, то выполняем //сброс значения m_number на 0
if (m_number == 8)
m_number = 0;
// В противном случае, просто увеличиваем m_number на единицу
else
++m_number;
return *this;
}
Number& Number::operator--() {
// Если значением переменной m_number является 0, то присваиваем //m_number значение 8
if (m_number == 0)
m_number = 8;
// В противном случае, просто уменьшаем m_number на единицу
else
--m_number;
return *this;
}
Number Number::operator++(int) {
// Создаем временный объект класса Number с текущим значением //переменной m_number
Number temp(m_number);
// Используем оператор инкремента версии префикс для реализации //перегрузки оператора инкремента версии постфикс
++(*this); // реализация перегрузки
// Возвращаем временный объект
return temp;
}
Number Number::operator--(int) {
// Создаем временный объект класса Number с текущим значением //переменной m_number
Number temp(m_number);
// Используем оператор декремента версии префикс для реализации //перегрузки оператора декремента версии постфикс
--(*this); // реализация перегрузки
// Возвращаем временный объект
return temp;
}
std::ostream& operator<< (std::ostream &out, const Number &n) {
out << n.m_number;
return out;
}
