The problem is that you declared operator>>
and operator<<
as non-member functions, but defined as a member function.
This should fix that problem (but open another set of problems). So instead of
ostream& Fraction::operator<<(ostream &os, Fraction& n) { ... istream& Fraction::operator>>(istream &os, Fraction& n) { ...
implement as :
ostream& operator<<(ostream &os, Fraction& n) { ... istream& operator>>(istream &os, Fraction& n) { ...
Also, take a note that you declared functions as :
friend ostream& operator<<(ostream &os, const Fraction& n); friend istream& operator>>(istream &is, const Fraction& n);
but defined as (therefore you changed the signature) :
ostream& Fraction::operator<<(ostream &os, Fraction& n) istream& Fraction::operator>>(istream &os, Fraction& n)
Proper way is to declare and define as :
ostream& Fraction::operator<<(ostream &os, const Fraction& n) istream& Fraction::operator>>(istream &os, Fraction& n)
I am adding just changes. The rest is the same as in the question:
class Fraction{ friend ostream& operator<<(ostream &os, const Fraction& n); friend istream& operator>>(istream &is, Fraction& n); // the rest is the same }; ostream& operator<<(ostream &os, const Fraction& n) { if (n.numera == 0) { cout << 0 << endl; return os; } else if (n.numera == n.denom) { cout << 1 << endl; return os; } else { cout << n.numera << '/' << n.denom << endl; return os; } } istream& operator>>(istream &os, Fraction& n) { char slash = 0; return os >> n.numera >> slash >> n.denom; }