Перегрузка операторов
Ключевое слово operator используется для создания перегруженных функций-операторов. Функции-операторы существуют в двух ипостасях: члена и не члена. Общая форма записи функции-оператора как члена имеет следующий вид.
тип_возврата имя_класса :: operator # (список_параметров)
{
//...
}
Здесь тип_возврата означает тип значения, возвращаемого функцией, имя_класса — имя класса, для которого перегружается этот оператор, а элемент # — сам перегружаемый оператор. При перегрузке унарного оператора список_параметров пуст. Операнд передаётся неявным образом в указателе this. При перегрузке бинарного оператора список_параметров задаёт операнд справа от оператора. Операнд слева передаётся неявным образом в указателе this. Например, следующий код создаёт тип данных "вектор".
class vector{
int x, y, z;
public:
vector operator+ (vector t);
vector operator= (vectort);
vector operator++ (void);
void show (void);
void assign (int mx, int my, int mz);
}
vector vector :: operator+ (vector t)
{
vector temp;
temp.x = x + t.x;
temp.y = y + t.y;
temp.z = z + t.z;
return temp;
}
vector vector :: operator= (vector t)
{
x = t.x;
y = t.y;
z = t.z;
return *this;
}
vector vector :: operator++ (void)
{
x++;
y++;
z++
return *this;
}
void vector :: show (void)
{
cout << x << ",";
cout << y << ",";
cout << z << " \n";
}
void vector :: assign (int mx, int my, int mz)
{
x = mx;
y = my;
z = mz;
}
main (void)
{
vector a, b, c;
a.assign (1, 2, 3);
b.assign (10, 10, 10);
a.show();
b.show();
c = a + b;
c.show();
c = a + b + c;
c.show();
c++;
c.show();
}
Что касается функций-не членов, функция-оператор имеет следующую форму.
тип_возврата operator # (список_параметров)
{
//...
}
Здесь список_операторов содержит один параметр при перегрузке унарного оператора. При перегрузке бинарного оператора операнд слева передаётся в первом параметре, а операнд справа — во втором параметре.
Поскольку нельзя перегружать операторы для встроенных типов, можно создать, с помощью ключевого слова typedef, новый тип который будет аналогом необходимого. Например для сравнения переменных встроенного типа char, мы напишем следующее.
typedef struct { char *str} Item;
int operator < (const Item& a, const Item& b)
{
return strcmp (a.str, b.str) < 0;
}
Применительно к перегрузке операторов действует несколько ограничений. Нельзя изменять приоритет оператора. Нельзя также изменять количество операндов, требуемых оператором. Нельзя изменять значение оператора, связанного со встроенными типами данных языка C++. Нельзя создавать новый оператор. Операторы препроцессора # и ## не могут быть перегружены. Нельзя перегружать следующие операторы: . :: .* ? Дружественные функции-операторыОтличие дружественных функций-операторов от обычных функций-операторов, членов класса, состоит в том что для них не используется указатель this При объявлении дружественной функции оператора должны передаваться два аргумента для бинарных операторов и один для унарных операций. Например.
class vrctor{
int x, y, z;
public:
friend vector operator+ (vector t1, vector t2);
}
vector operator+ (vector t1, vector t2)
{
vector tmp;
tmp.x = t1.x + t2.x;
tmp.y = t1.x + t2.y;
tmp.z = t1.x + t2.z;
return temp;
}
Перегрузка операции индексации []Операция индексации рассматривается как бинарная операция, где первый оператор — объект класса, а второй — целочисленный индекс. Например.
class vector{
int v[3];
public:
int& operator[] (int i);
}
int& vector :: operator[] (int i)
{
return v[i];
}
//...
v[0] = 100; //ссылаемся на приватный член с помощью перегруженного оператора []
Перегрузка операции преобразования типа ()Операции преобразования типов можно также перегружать, при этом в виде оператора указывается тип данных. Например.
struct Item{
int item;
Item (int t){
item = t;
}
operator int(){
return item;
}
};
Item t (11);
cout << (int)t; //Напечатает число 11
|