89793

Перегрузка операций в классах

Лекция

Информатика, кибернетика и программирование

Поскольку в С++ операции, рассматриваются как функции, то их можно переопределять так, что они будут работать не только с числами, а даже с графическими объектами, строками и вообще с чем угодно.

Русский

2015-05-13

62.03 KB

3 чел.

Перегрузка операций в классах

Определение (перегрузка) операций в классах

Поскольку в С++ операции, рассматриваются как функции, то их можно переопределять так, что они будут работать не только с числами, а даже с графическими объектами, строками и вообще с чем угодно. 

C++ позволяет распространить действие любой стандартной операции на новые типы данных, вводимые пользователем. Распространить операцию на новые типы данных позволяет механизм перегрузки стандартных операций. В С++ число операций ограничено стандартным набором.

Перегружаемые операции:

  •  Арифметические и логические операторы
  •  Операторы сравнения и равенства
  •  Операторы присваивания
  •  Битовые операторы
  •  Операторы ++ и -- в постфиксном и префиксном значениях
  •  Операторы индексации массива []
  •  Вызов функции ()
  •  Оператор доступа к члену через указатель на объект -> и обращения к члену через указатель на член ->*
  •  Операторы перенаправления ввода >> и вывода <<
  •  Операторы new и delete

Для распространения действия операции на новые пользовательские типы данных программист определяет специальную функцию, называемую «операция-функция»:

тип_возвращаемого_значения operator знак_операции (спецификация _параметров_операции-функции) {операторы_тела_операции-функции}

Чтобы явная связь с классом была определена, операция-функция: 

  •  может быть компонентом класса,
  •  определена в классе как дружественная, 
  •  у нее должен быть хотя бы один параметр типа класс (или ссылка на класс).

При переопределении операции действуют следующие ограничения: 

  •   С++ не различает префиксные и постфиксные версии операций ++ и --. 
  •   операция, которую вы хотите определить, уже должна существовать в языке. Например, вы не можете определить операцию #. 
  •   нельзя переопределить следующие операции:  .     .*     ::    ?:
  •   переопределенные операции сохраняют свое первоначальное старшинство. 

При вызове операции-функции используется обычный вид бинарных операций:

C=A+B;

или полная форма вызова:

C=operator + (A,B);

Любая стандартная бинарная операция @ может быть перегружена с помощью нестатической операции-функции, входящей в число компонентов класса с одним параметром:

T operator @ (T x)

Тогда вызов операции A @ B с объектами A и B класса T в качестве операндов интерпретируется как вызов функции:

A.operator@(B)

Если @ обозначает любую унарную операцию, то выражения x@ и @x можно интерпретировать либо как x.операция@(), либо как операция@(x). Если описаны обе формы, то компилятор попытается разрешить неоднозначность путем сравнения аргументов. Аналогично, переопределение бинарной операции @ в x@y может толковаться либо x.операция@(y), либо операция@(x,y), и если определены обе формы, то компилятору требуется анализировать аргументы. 

Пример #11. Класс clock

class clock{

public:

clock (unsigned long i);//конструктор

void print() const;//вывод по формату

void tick();//добавляет 1 секунду

clock operator++(){tick(); return *this;};

clock operator –(clock c){return (tot_secs-c.tot_secs);};

friend clock operator +(clock c1, clock c2) { return (c1.tot_secs+c2.tot_secs);};

friend clock operator *(unsigned long m, clock c) {return (m*c.tot_secs);};

friend clock operator *(clock c, unsigned long m) {return (m*c);};

private:

unsigned long tot_secs, secs, mins, hours, days;

};

inline clock::clock(unsigned long i)

{tot_secs=i; secs=tot_secs% 60;

mins=(tot_secs / 60) % 60;

hours=(tot_secs / 3600) % 24;

days= tot_secs / 86400;}

void clock::tick()

{ clock temp=clock(++tot_secs);

secs=temp.secs; mins=temp.mins;

hours=temp.hours; days=temp.days;}

void clock::print() const {

cout<<days<<“ д:”<<hours<<“ ч:” <<mins<<“  м:”<<secs<<“ с:”<< endl;}

int main()

{ clock::clock t1(59), t2(172799);

cout<<“начальное время”<<endl;

t1.print(); t2.print();

++t1; ++t2;

cout<<“время через секунду”<<endl;

t1.print(); t2.print();

return 0;

}

Пример #12. Массив

#include <iostream.h>

#include <assert.h>

class vect {

public:

explicit vect(int n=10);

//инициализация вектором vect (копирующий конструктор)

vect(const vect& v);

//инициализация массивом

vect(const int a[], int n);

~vect() {delete []p;}

int ub() const {return (size-1);}

int&  operator[] (int i);

vect& operator= (const vect& v);

vect operator+ (const vect& v);

private:

int* p; int size;

}

vect::vect(int n):size(n)

{ assert (n>0);

p=new int[size];

assert (p!=0);

}

vect::vect(const int a[], int n): size(n)

{   assert (n>0);

p=new int[size];

assert (p!=0);

for (int i=0; i<size; i++) p[i]=a[i];

}

vect::vect(const vect& v):size(v.size)

{ p=new int[size];

assert (p!=0);

for (int i=0; i<size; i++) p[i]=v.p[i];

}

int& vect::operator [] (int i)

//точно также можно определить оператор 

//индексирования (): int& vect::operator () (int i)

{ assert (i>=0 && i<size);

return p[i];

}

vect& vect::operator= (const vect& v)

{ if (this != &v)

{assert(v.size==size);

for (int i=0; i<size; ++i) p[i]=v.p[i];} return *this;}

vect vect::operator+ (const vect& v)

{ assert (v.size==size);int s=size;

vect sum(s);   

for (int i=0; i<s; ++i) sum.p[i]=p[i]+v.p[i];

return sum;

}

int main(){

vect A(3),B(3);

int i,b[5];

vect C(b,5), D(C);

for(i=0;i<3;i++){A[i]=i;} B=A;

for(i=0;i<3;i++){cout<<A[i]<<' ';} cout<<endl;

for(i=0;i<3;i++){cout<<B[i]<<' ';} cout<<endl;

A=A+B;

for(i=0;i<3;i++){cout<<A[i]<<' ';} cout<<endl;

return 0;

}

Пример #13. Перегруженные операторы ввода-вывода

class rational{//класс рациональных чисел

public:

rational (){}

~rational (){}

friend ostream& operator<< (ostream& out, rational x);

friend istream& operator>> (istream& in, rational& x);

private:

long a,q;

};

ostream& operator<<(ostream& out, rational x)

{return (out<<x.a<<“/”<<x.q<<‘\t’);};

istream& operator>> (istream& in, rational& x)

{return (in>>x.a>>x.q);};

int  main()

{

rational a,b;

cin>>a>>b;

cout<<a<<b;

return 0;

}

Пример #14. Операторы указателей

#include <iostream.h>

class triple{

public:

triple(int a, int b, int c)

{i=a; j=b; k=c;}

void print()

{cout<<“\ni=”<<i<<“, j=”<<j<<“, k=“<<k;}

private:

int i, j, k;

};

triple unauthor(0, 0, 0);

class t_ptr{

public:

t_ptr(bool f, triple* p)

{access=f; ptr=p;}

triple* operator->();

private:

bool access;

triple* ptr;

};

triple* t_ptr::operator->()

{

if (access) return (ptr);

else {cout<<

“\n Несанкционированный доступ”;

return &unauthor;}

}

int main()

{

triple a(1,2,3), b(4,5,6);

t_ptr ta(false, &a), tb(true, &b);

ta->print();//доступ запрещен

tb->print();//доступ предоставлен

return 0;

}


 

А также другие работы, которые могут Вас заинтересовать

21582. НЕОТЕКТОНИКА И РЕЛЬЕФ 52.5 KB
  Геоморфологические методы исследования новейших структур и движений 10. Геофизичекие аэрокосмические и другие методы изучения неотектоники 10. Геоморфологические методы исследования новейших структур и движений Выражение структур в облике земной поверхности обуславливается следующими факторами: спецификой геометрии структур размерности морфологии плановых очертаний; спецификой проявления экзогенных процессов изменениями морфологии и строения экзогенных форм рельефа под влиянием растущей структуры; составом свойствами и...
21583. МЕТОДЫ ГЕОМОРФОЛОГИЧЕСКИХ ИССЛЕДОВАНИЙ 44.5 KB
  Морфографические методы основаны на непосредственном наблюдении внешнего облика форм и элементов рельефа выявлении их особенностей и типических черт с целью морфологической классификации и описания а также изучения их пространственных взаимосвязей. Морфометрические методы основаны на применении количественных критериев к анализу форм рельефа и соответствующего генетического истолкования получаемого результата. Стратиграфический метод предназначен для установления геологического возраста отложений и форм рельефа....
21584. ОСНОВЫ ЧЕТВЕРТИЧНОЙ ГЕОЛОГИИ 44 KB
  Особенности антропогеновых отложений 12. Практическое и теоретическое значение изучения антропогеновых отложений 12. ОСНОВЫ ЧЕТВЕРТИЧНОЙ ГЕОЛОГИИ Последний период геологического развития Земли именуется по разному: четвертичный период по бытовавшему в 18 веке делению всех отложений на четыре формации ледниковый период новейший период плейстоцен антропоген. Ляйелем для отложений содержащих в составе морской фауны до 90 современных видов.
21585. МЕТОДЫ ИЗУЧЕНИЯ ЧЕТВЕРТИЧНЫХ ОТЛОЖЕНИЙ 33 KB
  МЕТОДЫ ИЗУЧЕНИЯ ЧЕТВЕРТИЧНЫХ ОТЛОЖЕНИЙ 13. Геологические методы 13. Геоморфологические методы 13. Геофизические методы 13.
21586. ОСНОВЫ СТРАТИГРАФИИ АНТРОПОГЕНА 34.5 KB
  лет назад 5 млн. лет назад в Африке возникли австралопитеки южные обезьяны освоившие прямохождение. лет назад от австралопитеков произошли первые гоминиды и их поздние представители относятся к роду Ноmo habilis человек умный. лет назад в Африке появились питекантропы первые представители архантропов древних людей.
21587. ЧЕТВЕРТИЧНЫЕ ОТЛОЖЕНИЯ НА ТЕРРИТОРИИ РОССИИ 45.5 KB
  ЧЕТВЕРТИЧНЫЕ ОТЛОЖЕНИЯ НА ТЕРРИТОРИИ РОССИИ 15. ЧЕТВЕРТИЧНЫЕ ОТЛОЖЕНИЯ НА ТЕРРИТОРИИ РОССИИ Территория нашей страны в структурнотектоническом отношении чрезвычайно разнообразна и поэтому разнообразны и палеогеографические обстановки накопления антропогеновых отложений. Краткая характеристика четвертичных отложений крупных геотектонических регионов страны Большая часть этих областей развивается по платформенному типу с конца протерозоя и поэтому в современном рельефе Русской равнины отражаются структурнотектонические формы заложенные в...
21588. Три подхода к изучению рельефа 42 KB
  Три подхода к изучению рельефа 1. ОБЩИЕ ВОПРОСЫ Геоморфология наука о формах рельефа современной поверхности его происхождении и развитии. Всестороннее изучение рельефа типизация наблюдаемых форм выявление морфологических комплексов форм рельефа их связи между собой с геологическим строением с континентальными отложениями. Выявление истории развития рельефа.
21589. ОБЩИЕ СВЕДЕНИЯ ОБ ОСНОВНЫХ ЗАКОНОМЕРНОСТЯХ ФОРМИРОВАНИЯ РЕЛЬЕФА И КОНТИНЕНТАЛЬНЫХ ОТЛОЖЕНИЙ 154 KB
  ОБЩИЕ СВЕДЕНИЯ ОБ ОСНОВНЫХ ЗАКОНОМЕРНОСТЯХ ФОРМИРОВАНИЯ РЕЛЬЕФА И КОНТИНЕНТАЛЬНЫХ ОТЛОЖЕНИЙ 2. Основные факторы генетических классификаций форм рельефа 2. Методы определения возраста рельефа и отложений 2. ОБЩИЕ СВЕДЕНИЯ ОБ ОСНОВНЫХ ЗАКОНОМЕРНОСТЯХ ФОРМИРОВАНИЯ РЕЛЬЕФА И КОНТИНЕНТАЛЬНЫХ ОТЛОЖЕНИЙ 2.
21590. РЕЛЬЕФООБРАЗУЮЩЕЕ ЗНАЧЕНИЕ ВЫВЕТРИВАНИЯ И МЕРЗЛОТНЫХ ПРОЦЕССОВ 62.5 KB
  РЕЛЬЕФООБРАЗУЮЩЕЕ ЗНАЧЕНИЕ ВЫВЕТРИВАНИЯ И МЕРЗЛОТНЫХ ПРОЦЕССОВ 3. Краткий обзор процессов выветривания 3. РЕЛЬЕФООБРАЗУЮЩЕЕ ЗНАЧЕНИЕ ВЫВЕТРИВАНИЯ И МЕРЗЛОТНЫХ ПРОЦЕССОВ 3. Краткий обзор процессов выветривания Агентами выветривания являются солнечная инсоляция составные части атмосферы вода кислоты растительные и животные организмы.