W tym samouczku dowiemy się o przeciążaniu operatorów na podstawie przykładów.
W C ++ możemy zmienić sposób działania operatorów dla typów zdefiniowanych przez użytkownika, takich jak obiekty i struktury. Nazywa się to przeciążeniem operatora . Na przykład,
Załóżmy, że utworzyliśmy trzy obiekty c1, c2 i wynikają z klasy o nazwie, Complex
która reprezentuje liczby zespolone.
Ponieważ przeciążanie operatorów pozwala nam zmienić sposób działania operatorów, możemy przedefiniować sposób działania +
operatora i użyć go do dodania liczb zespolonych c1 i c2, pisząc następujący kod:
result = c1 + c2;
zamiast czegoś takiego
result = c1.addNumbers(c2);
Dzięki temu nasz kod jest intuicyjny i łatwy do zrozumienia.
Uwaga: Nie można użyć operatora przeciążenia dla podstawowych typów danych, takich jak int
, float
, char
i tak dalej.
Składnia przeciążania operatora C ++
Aby przeciążać operatora, używamy specjalnej operator
funkcji.
class className (… public returnType operator symbol (arguments) (… )… );
Tutaj,
returnType
jest typem zwrotu funkcji.- operator jest słowem kluczowym.
symbol
jest operatorem, którego chcemy przeciążać. Takich jak:+
,<
,-
,++
, itd.arguments
to argumenty przekazane do funkcji.
Przeciążanie operatorów w operatorach jednoargumentowych
Operatory jednoargumentowe działają tylko na jednym operandzie. Operator inkrementacji ++
i operator dekrementacji --
to przykłady operatorów jednoargumentowych.
Przykład1: Przeciążenie operatora ++ (operator jednoargumentowy)
// Overload ++ when used as prefix #include using namespace std; class Count ( private: int value; public: // Constructor to initialize count to 5 Count() : value(5) () // Overload ++ when used as prefix void operator ++ () ( ++value; ) void display() ( cout << "Count: " << value << endl; ) ); int main() ( Count count1; // Call the "void operator ++ ()" function ++count1; count1.display(); return 0; )
Wynik
Liczba: 6
Tutaj, kiedy używamy ++count1;
, void operator ++ ()
nazywa się. Zwiększa to atrybut wartości obiektu count1 o 1.
Uwaga: kiedy przeciążamy operatorów, możemy go użyć do pracy w dowolny sposób. Na przykład moglibyśmy ++
zwiększyć wartość o 100.
Jednak to sprawia, że nasz kod jest zagmatwany i trudny do zrozumienia. Naszym zadaniem jako programisty jest właściwe, spójne i intuicyjne wykorzystanie przeciążenia operatora.
Powyższy przykład działa tylko wtedy, gdy ++
jest używany jako przedrostek. Aby ++
działać jako postfix, używamy tej składni.
void operator ++ (int) ( // code )
Zwróć uwagę na int
wewnętrzne nawiasy. Jest to składnia używana do używania jednoargumentowych operatorów jako przyrostka; to nie jest parametr funkcji.
Przykład 2: Przeciążenie operatora ++ (operator jednoargumentowy)
// Overload ++ when used as prefix and postfix #include using namespace std; class Count ( private: int value; public: // Constructor to initialize count to 5 Count() : value(5) () // Overload ++ when used as prefix void operator ++ () ( ++value; ) // Overload ++ when used as postfix void operator ++ (int) ( ++value; ) void display() ( cout << "Count: " << value << endl; ) ); int main() ( Count count1; // Call the "void operator ++ (int)" function count1++; count1.display(); // Call the "void operator ++ ()" function ++ count1; count1.display(); return 0; )
Wynik
Liczba: 6 Liczba: 7
Przykład 2 działa, gdy ++
jest stosowany zarówno jako prefiks i postfix. Jednak nie działa, jeśli spróbujemy zrobić coś takiego:
Count count1, result; // Error result = ++count1;
Dzieje się tak, ponieważ typ zwracany przez naszą funkcję operatora to void
. Możemy rozwiązać ten problem, wykonując Count
jako zwracany typ funkcji operatora.
// return Count when ++ used as prefix Count operator ++ () ( // code ) // return Count when ++ used as postfix Count operator ++ (int) ( // code )
Przykład 3: Wartość zwracana z funkcji operatora (operator ++)
#include using namespace std; class Count ( private: int value; public : // Constructor to initialize count to 5 Count() : value(5) () // Overload ++ when used as prefix Count operator ++ () ( Count temp; // Here, value is the value attribute of the calling object temp.value = ++value; return temp; ) // Overload ++ when used as postfix Count operator ++ (int) ( Count temp; // Here, value is the value attribute of the calling object temp.value = ++value; return temp; ) void display() ( cout << "Count: " << value << endl; ) ); int main() ( Count count1, result; // Call the "Count operator ++ ()" function result = ++count1; result.display(); // Call the "Count operator ++ (int)" function result = count1++; result.display(); return 0; )
Wynik
Liczba: 6 Liczba: 7
Tutaj użyliśmy następującego kodu do przeciążenia operatora prefiksu:
// Overload ++ when used as prefix Count operator ++ () ( Count temp; // Here, value is the value attribute of the calling object temp.value = ++value; return temp; )
Kod dla przeciążenia operatora postfiksowego jest również taki sam. Zwróć uwagę, że utworzyliśmy obiekt temp i zwróciliśmy jego wartość do funkcji operatora.
Zwróć też uwagę na kod
temp.value = ++value;
Wartość zmiennej należy do obiektu count1 w, main()
ponieważ count1 wywołuje funkcję, a temp.value należy do obiektu temp.
Przeciążanie operatorów w operatorach binarnych
Operatory binarne działają na dwóch operandach. Na przykład,
result = num + 9;
Tutaj +
jest operatorem binarnym, który działa na operandach num i 9
.
Kiedy przeciążamy operator binarny dla typów zdefiniowanych przez użytkownika przy użyciu kodu:
obj3 = obj1 + obj2;
Funkcja operatora jest wywoływana przy użyciu obiektu obj1, a obj2 jest przekazywana jako argument do funkcji.
Przykład 4: Przeciążanie operatorów binarnych w języku C ++
// C++ program to overload the binary operator + // This program adds two complex numbers #include using namespace std; class Complex ( private: float real; float imag; public: // Constructor to initialize real and imag to 0 Complex() : real(0), imag(0) () void input() ( cout <> real; cin>> imag; ) // Overload the + operator Complex operator + (const Complex& obj) ( Complex temp; temp.real = real + obj.real; temp.imag = imag + obj.imag; return temp; ) void output() ( if (imag < 0) cout << "Output Complex number: " << real << imag << "i"; else cout << "Output Complex number: " << real << "+" << imag << "i"; ) ); int main() ( Complex complex1, complex2, result; cout << "Enter first complex number:"; complex1.input(); cout << "Enter second complex number:"; complex2.input(); // complex1 calls the operator function // complex2 is passed as an argument to the function result = complex1 + complex2; result.output(); return 0; )
Wynik
Podaj pierwszą liczbę zespoloną: Wprowadź odpowiednio część rzeczywistą i urojoną: 9 5 Wprowadź drugą liczbę zespoloną: Wprowadź odpowiednio części rzeczywistą i urojoną: 7 6 Dane wyjściowe Liczba zespolona: 16 + 11i
W tym programie funkcja operatora to:
Complex operator + (const Complex& obj) ( // code )
Zamiast tego moglibyśmy również napisać tę funkcję, taką jak:
Complex operator + (Complex obj) ( // code )
Jednak,
- using
&
sprawia, że nasz kod jest wydajny, odwołując się do obiektu complex2 zamiast tworzyć zduplikowany obiekt wewnątrz funkcji operatora. - używanie
const
jest uważane za dobrą praktykę, ponieważ zapobiega modyfikowaniu kompleksu przez funkcję operatora2.

Rzeczy do zapamiętania w przeciążaniu operatorów C ++
- Dwa operatory
=
i&
są już domyślnie przeciążone w C ++. Na przykład, aby skopiować obiekty tej samej klasy, możemy bezpośrednio użyć=
operatora. Nie musimy tworzyć funkcji operatora. - Przeciążanie operatorów nie może zmienić pierwszeństwa i asocjatywności operatorów. Jeśli jednak chcemy zmienić kolejność ocen, należy użyć nawiasów.
- Istnieją 4 operatory, których nie można przeciążać w C ++. Oni są:
::
(rozdzielczość zakresu).
(wybór członków).*
(wybór elementu przez wskaźnik do funkcji)?:
(operator trójskładnikowy)
Odwiedź te strony, aby dowiedzieć się więcej na temat:
- Jak we właściwy sposób przeciążać operatora inkrementacji?
- Jak przeciążyć operator binarny - odjąć liczby zespolone?