OOP C++ first compiler error - c++

Please help this newbie, here's my code:
#include <iostream>
using namespace std;
class Complex {
private:
float r, i;
public:
Complex(float rr, float ii) : r(rr), i (ii) {}
float GiveRe () { return r; }
float GiveIm () { return i; }
void Setit (float rr, float ii) {
r = rr;
i = ii;
}
};
Complex a(10, 20);
Complex sumit (Complex &ref) {
static Complex sum (0, 0);
sum.Setit(sum.GiveRe() + ref.GiveRe(), sum.GiveIm() + ref.GiveIm());
return sum;
}
int main () {
Complex sumvalue = sumit (a);
cout << sumvalue << endl;
return 0;
}
error: no match for 'operator<<' in 'std::cout << sumvalue'.
The program should output the sum of a complex number.

cout can't tell what you want to output, you need to specify the operator<< in the class or make it possible to implicitly convert your class to a compatible type.
http://www.cplusplus.com/reference/iostream/ostream/operator%3C%3C/
Rudolf Mühlbauer's code as implemented in your class:
Add this somewhere within the class header:
friend ostream& operator<<(ostream& out, const Complex& compl);
and this below the header:
ostream& operator<<(ostream& out, const Complex& compl)
{
return out << compl.r << "/" << compl.i;
}
Implementation should be changed to suit your exact needs.

Complex doesn't have an operator <<
ostream& Complex::operator << ( ostream& os )
{
// use os << field/method here to out put
return os;
}
Also if complex can be displayed to console in different ways, then you should think of using methods to display instead of cout <<
void Complex::DisplayToConsole()
{
std::cout << r << " " << i << '\n';
}

You have to overload the "<<" operator for Complex type.
#include <iostream>
using namespace std;
class Complex {
private:
float r, i;
public:
Complex(float rr, float ii) : r(rr), i (ii) {}
float GiveRe () { return r; }
float GiveIm () { return i; }
void Setit (float rr, float ii) {
r = rr;
i = ii;
}
};
ostream& operator<<(ostream& os, Complex& c)
{
float i;
os<<c.GiveRe();
if(c.GiveIm() < 0){
os<<"-j"<<c.GiveIm()*(-1);
}else{
os<<"+j"<<c.GiveIm();
}
return os;
}
Complex a(10, 20);
Complex sumit (Complex &ref) {
static Complex sum (0, 0);
sum.Setit(sum.GiveRe() + ref.GiveRe(), sum.GiveIm() + ref.GiveIm());
return sum;
}
int main () {
Complex sumvalue = sumit (a);
cout << sumvalue << endl;
return 0;
}

A complete minimal example:
#include <iostream>
using namespace std;
class C {
public:
int r, l;
// if the operator needs access to private fields:
friend ostream& operator<< (ostream&, const C&);
};
ostream& operator << (ostream& stream, const C& c) {
stream << c.r << "--" << c.l;
return stream;
}
int main() {
C c;
c.l = 1;
c.r = 2;
cout << c << endl;
}
C++ allows you to define operators. The STL uses the << operator for output, and the whole istream/ostream class hierarchy uses this operator to input/output.
Operators are implemented as functions, but always follow a very specific syntax. As in the example, ostream& operator << (ostream&, const MYTYPEHERE&) is the way to define ostream << operators.
When C++ encounters a statement, it has to deduce the types of all operands, and find (quite magically, indeed) a solution to the question: given my operands and operators, can i find a typing such that the statement gets valid?
These ofstream operators are defined for all basic types somewhere in <iostream>, so if you write cout << 10, the compiler finds an operator ostream& operator<< (ostream&, int).
If you want to be able to use userdefined types in this game, you have to define the operators. otherwise, a statement cout << sometype will not be valid. This is also the reason for the harsh compiler errors sometimes found in C++: "Well, i have some operators << defined, but none is compatible with your type!".
Because sometimes it is not favourable to implement operators for your types (if you only output them once, e.g.), i suggested to write:
cout << sum.re << "--" << sum.im << endl; // or similar
This way, you write less code, and you are flexible in the output format. Who knows if you want you complex number formatted differently next time? But this is another discussion.
Why complicating that much? Because C++ can be awfully complicated. It it very powerfull, but crammed with special syntax and exceptions to those. In the end, the difference to C lies exactly here: C++ does a much better job with type inference (needed for templates), often resulting in WTF?
On how to implement it in your code, i think the other answers provide nice solutions!

sumit(a) returns an object of type Complex, which cout was not defined to handle.

Related

no operator "<<" matches these operands when using operator overloading

Error ocurred with the following try to operator overloading:
#include<iostream>
#include<string>
#include<ostream>
using namespace std;
class Dollar
{
private:
float currency, mktrate, offrate;
public:
Dollar(float);
float getDollar() const;
float getMarketSoums() const;
float getofficialSoums() const;
void getRates();
// In the following function I was trying to overload "<<" in order to print all the data members:
friend void operator<<(Dollar &dol, ostream &out)
{
out << dol.getDollar() << endl;
out << dol.getMarketSoums() << endl;
out << dol.getofficialSoums() << endl;
}
};
Dollar::Dollar(float d)
{
currency = d;
}
float Dollar::getDollar() const
{
return currency;
}
float Dollar::getMarketSoums() const
{
return mktrate;
}
float Dollar::getofficialSoums() const
{
return offrate;
}
void Dollar::getRates()
{
cin >> mktrate;
cin >> offrate;
}
int main()
{
Dollar dollar(100);
dollar.getRates();
// In this line I am getting the error. Could you please help to modify it correctly?
cout << dollar;
system("pause");
return 0;
}
You have to pass std::ostream object as the first parameter to the insertion operator << not as the second one as long as you are calling it that way:
friend void operator << (ostream &out, Dollar &dol);
You should make the object passed in to the insertion operator constant reference as long as this function is only prints and not intending to modify the object's members:
friend void operator << (ostream &out, const Dollar& dol);
So pass by reference to avoid multiple copies and const to avoid unintentional modification.
If you want to invoke to get it work the way you wanted you can do this:
friend void operator<<(const Dollar &dol, ostream &out){
out << dol.getDollar() << endl;
out << dol.getMarketSoums() << endl;
out << dol.getofficialSoums() << endl;
}
And in main for example:
operator << (dollar, cout); // this is ok
dollar << cout; // or this. also ok.
As you can see I reversed the order of calling the insertion operator to match the signature above. But I don't recommend this, it is just to understand more how it should work.

Error with << operator overload returning a std::string

I'm having troubles understanding the reason why the compiler accuses error, when the return type of a << operator overload is std::string. Could you please help me understand?
Bellow is an reproducible example, which gives a gigantic error.
class XY
{
int X__;
int Y__;
public:
XY(int x, int y):X__(x), Y__(y){}
~XY(){}
std::string operator<<(const XY_cartesiano& c)
{
std::stringstream ss;
ss << "{ " << X__ << ", " << Y__ << " }";
return ss.str();
}
int x() const{return X__;}
int y() const{return Y__;}
};
void main()
{
XY a(1,2);
std::cout << a;
}
Let's take something like this as an example:
cout << "My number is " << 137 << " and I like it a lot." << endl;
This gets parsed as
((((cout << "My number is ") << 137) << " and I like it a lot.") << endl);
In particular, notice that the expression cout << "My number is " has to evaluate to something so that when we then try inserting 137 with << 137 the meaning is "take 137 and send it to cout."
Imagine if cout << "My number is " were to return a string. In that case, the << 137 bit would try to use the << operator between a string on the left-hand side and an int on the right-hand side, which isn't well-defined in C++.
The convention is to have the stream insertion operator operator << return a reference to whatever the left-hand side stream is so that these operations chain well. That way, the thing on the left-hand side of << 137 ends up being cout itself, so the above code ends up essentially being a series of chained calls to insert things into cout. The signature of these functions therefore usually look like this:
ostream& operator<< (ostream& out, const ObjectType& myObject) {
// ... do something to insert myObject into out ... //
return out;
}
Now, everything chains properly. Notice that this function is a free function, not a member function, and that the left-hand side is of type ostream and the right-hand side has the type of your class in it. This is the conventional way to do this, since if you try overloading operator << as a member function, the left-hand side will be an operand of your class type, which is backwards from how stream insertion is supposed to work. If you need to specifically access private fields of your class in the course of implementing this function, make it a friend:
class XY {
public:
...
friend ostream& operator<< (ostream& out, const XY& myXY);
};
ostream& operator<< (ostream& out, const XY &myXY) {
...
return out;
}
Correct way to overload << operator in your case is
ostream& operator<<(ostream& os, const XY& c)
{
os << c.X__ <<" "<< c.Y__ ;
return os;
}
You have overloaded operator<< in a way that's incompatible with the conventions you must follow when you intend to use the operator with a std::ostream object like std::cout.
In fact, your operator<<'s signature has nothing to do with streams at all! It is just a member function of XY which takes another XY (which it then does not use), returns a string and has an unsual name. Here's how you would theoretically call it:
XY a(1,2);
XY b(1,2);
std::string x = (a << b);
The correct way to overload operator<< for use with streams is to make the operator a non-member function, add a stream reference parameter and return a stream reference to the stream argument. You also do not need a string stream; you write directly to the stream you get:
#include <iostream>
class XY
{
int x;
int y;
public:
XY(int x, int y) : x(x), y(y) {}
int X() const { return x; }
int Y() const { return y; }
};
std::ostream& operator<<(std::ostream& os, XY const& c)
{
os << "{ " << c.X() << ", " << c.Y() << " }";
return os;
}
int main()
{
XY a(1,2);
std::cout << a;
}

Problems with ostream

I'm working in a Big Integer implementation in C++ and I'm trying to use cout with my BigInt class. I already overloaded the << operator but it doesn't work in some cases.
Here is my code:
inline std::ostream& operator << (ostream &stream, BigInt &B){
if (!B.getSign()){
stream << '-';
}
stream << B.getNumber();
return stream;
}
The code above works with:
c = a + b;
cout << c << endl;
But fails with:
cout << a + b << endl;
In the first case the program runs fine, but in the second the compiler gave an error:
main.cc: error: cannot bind ‘std::ostream {aka std::basic_ostream<char>}’ lvalue to ‘std::basic_ostream<char>&&’
It's possible to overload the << operator for function in both cases?
Methods:
string getNumber ();
bool getSign ();
string BigInt::getNumber (){
return this->number;
}
bool BigInt::getSign (){
return this->sign;
}
As chris already pointed out in comments very quickly (as usual), you have a temporary created in here:
cout << a + b << endl;
You cannot bind that to a non-const reference. You will need to change the signature of your operator overloading by adding the const keyword to the reference.
This code works for me with a dummy BigInt implementation (as you have not shared yours):
#include <iostream>
using namespace std;
class BigInt
{
public:
bool getSign() const { return true; }
int getNumber() const { return 0; }
const BigInt operator+(const BigInt &other) const {}
};
inline std::ostream& operator << (ostream &stream, const BigInt &B){
// ^^^^^
if (!B.getSign()){
stream << '-';
}
stream << B.getNumber();
return stream;
}
int main()
{
BigInt a, b, c;
c = a + b;
cout << c << endl;
cout << a + b << endl;
return 0;
}
But yeah, I agree that the error message is not self-explanatory in this particular case.
Change
inline std::ostream& operator << (ostream &stream, BigInt &B){
to
inline std::ostream& operator << (ostream &stream, BigInt const& B){
c can be a used where BiInt& is expected but a+b cannot be because a+b is a temporary. But it can be used where BigInt const& is expected.

overloading operator * c++

I have been trying to compile this program but it is giving me an error in regards to overloading the * operator for one of the functions: complex operator *(double n)const
When I try to compile I get the error: no match for 'operator*' in '2 * c'
Here is the header file:
Complex.h
#ifndef COMPLEX0_H
#define COMPLEX0_H
class complex {
double realNum;
double imagNum;
public:
complex();
complex(double x,double y);
complex operator *(double n)const;
complex operator *(const complex &c1)const;
friend std::istream &operator>>(std::istream &is,complex &cm);
friend std::ostream &operator<<(std::ostream &os,const complex &cm);
};
#endif
Here is the cpp:
Complex.cpp
#include "iostream"
#include "complex0.h"
complex::complex() {
imagNum = 0.0;
realNum = 0.0;
}
complex::complex(double x, double y) {
realNum = x;
imagNum = y;
}
complex complex::operator *(const complex& c1) const{
complex sum;
sum.realNum=realNum*c1.realNum-c1.imagNum*imagNum;
sum.imagNum=realNum*c1.imagNum+imagNum*c1.realNum;
return sum;
}
complex complex::operator *(double n)const{
complex sum;
sum.realNum=realNum*n;
sum.imagNum=imagNum*n;
return sum;
}
std::istream &operator >>(std::istream& is, complex& cm) {
is >> cm.realNum>> cm.imagNum;
return is;
}
std::ostream &operator <<(std::ostream& os, const complex& cm){
os<<"("<<cm.realNum<<","<<cm.imagNum<<"i)"<<"\n";
return os;
}
main.cpp
#include <iostream>
using namespace std;
#include "complex0.h"
int main() {
complex a(3.0, 4.0);
complex c;
cout << "Enter a complex number (q to quit):\n";
while (cin >> c) {
cout << "c is " << c << "\n";
cout << "a is " << a << "\n";
cout << "a * c" << a * c << "\n";
cout << "2 * c" << 2 * c << "\n";
cout << "Enter a complex number (q to quit):\n";
}
cout << "Done!\n";
return 0;
}
Can someone explain to me what I have done wrong?
The member function operator only applies when the first operand is of your class type. If you want to handle the case where the second operand is of your type, you need also a free function (in which we simply delegate to the member function by virtue of commutativity of the operation):
complex operator*(double n, complex const & x)
{
return x * n;
}
(Please note that the standard library already contains <complex>.)
You have a member function defined as follows:
complex complex::operator *(double n) const;
That will let you do things like: complex_number * 3.0, but not 3.0 * complex_number. However, you can't create a member function that will let you do 3.0 * complex_number. The only place you could create that member function, is inside the definition of double, which you can't change.
Instead of doing it as member functions though, you can also do it as free-standing functions:
complex operator*(complex x, double n); // Called for complex_number * 2.0
complex operator*(double n, complex x); // Called for 2.0 * complex_number

C++ Template >> and << overloading trouble

Ok so I am trying to write a template that builds a 2D matrix, and I want the >> and << to work as normal, here is the code I have so far but I am lost. I have functions input and output to run a user through filling the template at the moment, so I want to be able to cin and cout the template.
#include <iostream>
#include <cstdlib>
using namespace std;
template <typename T >
class Matrix
{
friend ostream &operator<<(ostream& os,const Matrix& mat);
friend istream &operator>>(istream& is,const Matrix& mat);
private:
int R; // row
int C; // column
T *m; // pointer to T
public:
T &operator()(int r, int c){ return m[r+c*R];}
T &operator()(T a){for(int x=0;x<a.R;x++){
for(int z=0;z<a.C;z++){
m(x,z)=a(x,z);
}
}
}
~Matrix();
Matrix(int R0, int C0){ R=R0; C=C0; m=new T[R*C]; }
void input(){
int temp;
for(int x=0;x<m.R;x++){
for(int y=0;y<m.C;y++){
cout<<x<<","<<y<<"- ";
cin>>temp;
m(x,y)=temp;
}
}
}
};
// istream &operator>>(istream& is,const Matrix& mat){
// is>>mat
// };
ostream &operator<<(ostream& os,const Matrix& mat){
for(int x=0;x<mat.R;x++){
for(int y=0;y<mat.C;y++){
cout<<"("<<x<<","<<y<<")"<<"="<<mat.operator ()(x,y);
}
}
};
int main()
{
Matrix<double> a(3,3);
a.input();
Matrix<double> b(a);
cout<<b;
cout << a(1,1);
}
Here are all the problems I found with your code. Let's start from the beginning:
Wrong function return-type and assignment through this
T operator>>(int c)
{
this = c;
}
Why is this code wrong? Well the first thing I notice is that your function is returning T yet you have no return statement present in the block. Forget about what I said in the comments, your insertion/exertion operators should return *this. It follows that your return-type should be Maxtrix&.
Another error I see in this snippet is that you are assigning the this pointer. This shouldn't have compiled for you. Rather, if you meant to change a certain data member (preferably your C data member), it should have looked like this:
this->C = c;
In turn, this is what your function should look like:
Matrix& operator>>(int c)
{
this->C = c;
return *this;
}
this->(z, x)
In the inner for loop of your output function, you did this:
cout << "(" << z << "," << x << ")" << "=" << this->(z, x) << endl;
this->(z, x) isn't doing what you think. It doesn't concurrently access two of the matrix's data members. It will actually cause an error because of invalid syntax. You'll have to access the data members separately, like this:
... << this->z << this->x << endl;
Moreover, this output function doesn't need a return-type. Just make it void.
Note that you have the same problem in your input function.