+, -, ==, etc.) for user-defined types<<) / extraction (>>): overloaded to enable custom objects to work with cout/cin-x, ++x) vs Binary operator (two operands, e.g., x + y) overloading follow different signaturesclass Complex
{
private:
double real, imag;
public:
Complex(double r = 0, double i = 0) : real(r), imag(i) {}
Complex operator+(const Complex& other)
{
return Complex(real + other.real, imag + other.imag);
}
friend ostream& operator<<(ostream& out, const Complex& c)
{
out << c.real << " + " << c.imag << "i";
return out;
}
};
// Complex a(3,4), b(1,2); cout << (a + b); --> 4 + 6i
Operators that CANNOT be overloaded: :: (scope resolution), . (member access), .* (pointer-to-member access), ?: (ternary), sizeof
Without overloading, combining two objects requires an awkward function call: addComplex(a, b) instead of the natural a + b. Overloading lets user-defined types read and behave like built-in types.
#include <iostream>
using namespace std;
class Complex
{
private:
double real, imag;
public:
Complex(double r = 0, double i = 0) : real(r), imag(i) {}
Complex operator+(const Complex& other) // binary operator, member function
{
return Complex(real + other.real, imag + other.imag);
}
bool operator==(const Complex& other) // comparison operator
{
return (real == other.real) && (imag == other.imag);
}
friend ostream& operator<<(ostream& out, const Complex& c); // needs friend -- see below
};
ostream& operator<<(ostream& out, const Complex& c)
{
out << c.real << " + " << c.imag << "i";
return out;
}
int main()
{
Complex a(3, 4), b(1, 2);
Complex sum = a + b; // calls operator+
cout << sum << endl; // 4 + 6i, calls operator<<
cout << (a == b) << endl; // 0 (false)
return 0;
}
operator<< must be a friend, not a membera + b works as a member function because the left operand (a) is the object calling operator+. But cout << c puts cout (an ostream) on the LEFT — you can't add a member function to the built-in ostream class, so operator<< must be a free function with friend access to Complex's private data.
:: (scope resolution), . (member access), .* (pointer-to-member access), ?: (ternary), sizeof — these are fixed by the language and always operate on their literal operands, not on overloaded semantics.
+ b) == c) :: (scope resolution) d) <<operator<< for a custom class is typically implemented as:
operator+ between two Complex objects lets you write:
add(a,b) only b) a + b directly, like built-in types c) Nothing different d) Only integer additionoperator+ work as a member function but operator<< cannot?