int main()
{
CComplex c1(9,9);
CComplex c3;
c3 = 5 + c1; // getting error here
c3.print();
cout << c3;
return 0;
}
CComplex CComplex::operator+(const CComplex &complex)
{
CComplex temp;
temp.m_real = complex.m_real + m_real;
temp.m_imaginary = complex.m_imaginary + m_imaginary;
return temp;
}
-
Not sure if this is a dupe: [What are the basic rules and idioms for operator overloading?](https://stackoverflow.com/questions/4421706/what-are-the-basic-rules-and-idioms-for-operator-overloading) (None of the answers seem to tackle the problem why you need 2 operator overloads) – Yksisarvinen Nov 15 '18 at 08:46
-
You need to overload the + operator for int and not complex. Like this: `operator+(int c)` – itsundefined Nov 15 '18 at 08:49
-
For future reference, please state and explain what the problem, what you have attempted, and attach the error in full to the question. – TrebledJ Nov 15 '18 at 08:54
-
@itsundefined A non-member overload `operator+(int, CComplex)` is required here. – Yksisarvinen Nov 15 '18 at 09:01
-
His question is not clear whether or not he wants to support both – itsundefined Nov 15 '18 at 09:02
2 Answers
You need overload +
operator for int
type and add some constructors if they are not defined
class CComplex
{
public:
CComplex()
: m_real(0), m_imaginary(0)
{ }
CComplex(double real)
: m_real(real), m_imaginary(0)
{ }
CComplex(double real, double imaginary)
: m_real(real), m_imaginary(imaginary)
{ }
CComplex operator + (const CComplex& complex)
{
CComplex temp;
temp.m_real = complex.m_real + m_real;
temp.m_imaginary = complex.m_imaginary + m_imaginary;
return temp;
}
double m_real;
double m_imaginary;
};
CComplex operator + (const int value, const CComplex& complex)
{
return CComplex(value) + complex;
}
std::ostream& operator << (std::ostream& os, const CComplex& complex)
{
os << "(" << complex.m_real << "," << complex.m_imaginary << ")";
return os;
}
int main()
{
CComplex c1(9,9);
CComplex c3;
c3 = 5 + c1; // no more error here
std::cout << c3;
return 0;
}
Result
(14,9)

- 992
- 5
- 8
-
Thank you for your quick response @serge . why can't we define the function inside the class. As there will be two overloaded function for the same operator. – yajnas Nov 15 '18 at 11:59
-
Yes, we can :) The method should be marked as `friend` for integer type overloading. – serge Nov 15 '18 at 12:43
-
The function does not need to be marked as `friend`. It only uses the public interface. In order to define that function inside the class it has to be `static`; otherwise it would expect a `CComplex` as its left-hand argument. – Pete Becker Nov 15 '18 at 14:47
-
@PeteBecker try to compile it as non-friend or static https://wandbox.org/permlink/xK6mASKu8XO2IvzP – serge Nov 15 '18 at 15:09
-
Again, perhaps more clearly: `friend` would give it access to private members. That function does not use any private members. There is a possible issue with defining different versions of an overloaded in different scopes, but `friend` is not the appropriate answer. – Pete Becker Nov 15 '18 at 17:08
-
@PeteBecker again, did you try to compile the example? The `<<` operator has access to private members. The `+` one potentially should have access, too. Take a look also at [Microsoft's example](https://learn.microsoft.com/en-us/cpp/standard-library/overloading-the-output-operator-for-your-own-classes) which uses `friend` and explain why Microsoft guys answer is "not appropriate". – serge Nov 16 '18 at 09:02
-
What private members? Everything in your code example is public. Regardless, the fact that you wrote a `<<` that wouldn't work if you wrote some other code differently doesn't change the fact that the `operator+` under discussion doesn't uses only obviously public interface functions. – Pete Becker Nov 16 '18 at 15:21
-
@PeteBecker did you try to compile your suggestion at least? Could you explain why Microsoft's example is not appropriate? – serge Nov 16 '18 at 15:24
-
Please stop. I didn't **suggest** anything. I haven't looked at Microsoft's example, and I have no intention of doing so. I made a simple statement about the code you presented. Nothing more. I stand by that statement: that `operator+` does not need to be a friend. It uses only public interface functions. – Pete Becker Nov 16 '18 at 15:26
-
@PeteBecker yes you do. 1/ _In order to define that function inside the class it has to be static_ 2/ try to compile the code without `friend` and/or with `static`. Please don't make suggestions that cannot be even compiled. – serge Nov 16 '18 at 15:46
I think the correct solution is:
class CComplex {
public:
CComplex();
CComplex(int); // NEW - CONVERSION CONSTRUCTOR
CComplex(double real);
CComplex(double real, double imaginary);
friend CComplex operator + (const CComplex& a, const CComplex& b); // FRIEND - NON-MEMBER FUNCTION
};
Please note these features in the code:
- There is a constructor getting one
int
parameter. This is a casting constructor that the compiler can use for automatic conversion from anint
toCComplex
. operator+
is a non-member function (friend
keyword makes the function non-member). It slightly differs from the situation whenoperator+
is a member function (CComplex operator+(CComplex const &b) const
).
If you write:
CComplex c1;
5 + c1;
Then for 5 + c1
there is searched an operator+
with parameters (int,CComplex)
. According to C++ standard there is allowed only one conversion to get proper parameter types (sorry I have no formal quotation). There is a conversion constructor from int
to CComplex
so there is automatically called this conversion constructor and then operator+(CComplex,CComplex)
with proper parameters.
If you didn't have CComplex(int)
constructor, then 5 + c1
would not work because there are needed TWO conversion from: int
to double
and from double
to CComplex
.
Additionaly, if operator+
was a member function (not friend
), it wouldn't work at all. Because according C++ standard there is no possibility of automatic conversion for the left operand. So even conversion constructor CComplex(int)
wouldn't help.
Plus: I think that overloading operator+
for types like (int, CComplex)
is not a good idea because it would cause explosion of declarations. The same you would need for operator-()
and for any order of operands - e.g. (CComplex,int)
, (CComplex,long)
, etc... By providing conversion constructor from required types you get all these combinations "automatically" and "for free".

- 1,077
- 6
- 18