Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > operator << and conversion operator

Reply
Thread Tools

operator << and conversion operator

 
 
cronusf
Guest
Posts: n/a
 
      10-27-2010
Suppose I have a class Complex and I overload operator double() to get
the real part. I also define:

std:stream& operator<<(std:stream& os, Complex& complex)
{
os << "(" << complex.real<< ", " << complex.imaginary << ")";

return os;
}

Now if I write:

Complex a(1.0, 2.0)
Complex b(1.0, 2.0)

cout << a + b << endl;

I have overloaded operator+ for Complex.
However, when I write this, it calls operator double() and outputs
that? Why? If I change to const Complex& it behaves as expected. If
I remove operator double() it behaves as expected and calls the
Complex overload of operator <<.
 
Reply With Quote
 
 
 
 
Garrett Hartshaw
Guest
Posts: n/a
 
      10-27-2010
On 10/26/2010 09:36 PM, cronusf wrote:
> Suppose I have a class Complex and I overload operator double() to get
> the real part. I also define:
>
> std:stream& operator<<(std:stream& os, Complex& complex)
> {
> os<< "("<< complex.real<< ", "<< complex.imaginary<< ")";
>
> return os;
> }
>
> Now if I write:
>
> Complex a(1.0, 2.0)
> Complex b(1.0, 2.0)
>
> cout<< a + b<< endl;
>
> I have overloaded operator+ for Complex.
> However, when I write this, it calls operator double() and outputs
> that? Why? If I change to const Complex& it behaves as expected. If
> I remove operator double() it behaves as expected and calls the
> Complex overload of operator<<.


I would think that this would not work because the expression a + b is a
temporary and therefore cannot bind to a non-const reference. Therefore
your operator<< for Complex& is not considered, and the compiler
searches for another operator<<. However, I do not know why it would
consider the Complex overload when operator double is removed.
--Garrett
 
Reply With Quote
 
 
 
 
Ian Collins
Guest
Posts: n/a
 
      10-27-2010
On 10/27/10 02:36 PM, cronusf wrote:
> Suppose I have a class Complex and I overload operator double() to get
> the real part. I also define:
>
> std:stream& operator<<(std:stream& os, Complex& complex)
> {
> os<< "("<< complex.real<< ", "<< complex.imaginary<< ")";
>
> return os;
> }
>
> Now if I write:
>
> Complex a(1.0, 2.0)
> Complex b(1.0, 2.0)
>
> cout<< a + b<< endl;
>
> I have overloaded operator+ for Complex.
> However, when I write this, it calls operator double() and outputs
> that? Why? If I change to const Complex& it behaves as expected.


Probably because the result of a+b is a temporary and you can't bind a
temporary to a non-const reference.

--
Ian Collins
 
Reply With Quote
 
cronusf
Guest
Posts: n/a
 
      10-27-2010
On Oct 26, 7:11*pm, Ian Collins <(E-Mail Removed)> wrote:
> On 10/27/10 02:36 PM, cronusf wrote:
>
>
>
> > Suppose I have a class Complex and I overload operator double() to get
> > the real part. *I also define:

>
> > std:stream& *operator<<(std:stream& *os, Complex& *complex)
> > {
> > * * os<< *"("<< *complex.real<< *", "<< *complex.imaginary<< *")";

>
> > * * return os;
> > }

>
> > Now if I write:

>
> > Complex a(1.0, 2.0)
> > Complex b(1.0, 2.0)

>
> > cout<< *a + b<< *endl;

>
> > I have overloaded operator+ for Complex.
> > However, when I write this, it calls operator double() and outputs
> > that? *Why? *If I change to const Complex& *it behaves as expected.

>
> Probably because the result of a+b is a temporary and you can't bind a
> temporary to a non-const reference.


That's what I thought at first, but If
I remove operator double() it behaves as expected and calls the
Complex overload of operator <<.
 
Reply With Quote
 
Ian Collins
Guest
Posts: n/a
 
      10-27-2010
On 10/27/10 05:34 PM, cronusf wrote:
> On Oct 26, 7:11 pm, Ian Collins<(E-Mail Removed)> wrote:
>> On 10/27/10 02:36 PM, cronusf wrote:
>>
>>
>>
>>> Suppose I have a class Complex and I overload operator double() to get
>>> the real part. I also define:

>>
>>> std:stream& operator<<(std:stream& os, Complex& complex)
>>> {
>>> os<< "("<< complex.real<< ", "<< complex.imaginary<< ")";

>>
>>> return os;
>>> }

>>
>>> Now if I write:

>>
>>> Complex a(1.0, 2.0)
>>> Complex b(1.0, 2.0)

>>
>>> cout<< a + b<< endl;

>>
>>> I have overloaded operator+ for Complex.
>>> However, when I write this, it calls operator double() and outputs
>>> that? Why? If I change to const Complex& it behaves as expected.

>>
>> Probably because the result of a+b is a temporary and you can't bind a
>> temporary to a non-const reference.

>
> That's what I thought at first, but If
> I remove operator double() it behaves as expected and calls the
> Complex overload of operator<<.


Well it shouldn't. You either have something else in your code you have
overlooked, or there's a bug in your compiler. Which compiler are you
using?

--
Ian Collins
 
Reply With Quote
 
Yakov Gerlovin
Guest
Posts: n/a
 
      10-27-2010
Interesting.
Just checked it on VC6/WinXp and on Solaris9/WS6 and the compilers
accepted both const and non-const versions of op<< for temp.
 
Reply With Quote
 
Ian Collins
Guest
Posts: n/a
 
      10-27-2010
On 10/27/10 11:38 PM, Leigh Johnston wrote:
> On 27/10/2010 11:36, Yakov Gerlovin wrote:
>> Interesting.
>> Just checked it on VC6/WinXp and on Solaris9/WS6 and the compilers
>> accepted both const and non-const versions of op<< for temp.

>
> Nobody cares what an old, broken compiler such as VC6 does. Use proper,
> standards compliant C++ compilers.


Sun WS6 is also well past its use by date.

--
Ian Collins
 
Reply With Quote
 
Öö Tiib
Guest
Posts: n/a
 
      10-28-2010
On 27 okt, 15:01, "Daniel T." <(E-Mail Removed)> wrote:
> In article
> <(E-Mail Removed)>,
>
>
>
> *cronusf <(E-Mail Removed)> wrote:
> > Suppose I have a class Complex and I overload operator double() to get
> > the real part. *I also define:

>
> > std:stream& operator<<(std:stream& os, Complex& complex)
> > {
> > * *os << "(" << complex.real<< ", " << complex.imaginary << ")";

>
> > * *return os;
> > }

>
> > Now if I write:

>
> > Complex a(1.0, 2.0)
> > Complex b(1.0, 2.0)

>
> > cout << a + b << endl;

>
> > I have overloaded operator+ for Complex.
> > However, when I write this, it calls operator double() and outputs
> > that? *Why? *If I change to const Complex& it behaves as expected. *If
> > I remove operator double() it behaves as expected and calls the
> > Complex overload of operator <<.

>
> Given the operator precedence, your expression is evaluated as:
>
> (cout << a) + (b << endl)


Not true by language parsing rules.
By standard it is evaluated like:

additive-expression:
multiplicative-expression
additive-expression + multiplicative-expression
additive-expression - multiplicative-expression

shift-expression:
additive-expression
shift-expression << additive-expression
shift-expression >> additive-expression

That results with:

((cout << (a + b)) << endl)

You probably mixed up precedence of << and % (that boost::format
overloads as separator).
 
Reply With Quote
 
cronusf
Guest
Posts: n/a
 
      10-28-2010
> >> Probably because the result of a+b is a temporary and you can't bind a
> >> temporary to a non-const reference.

>
> > That's what I thought at first, but If
> > I remove operator double() it behaves as expected and calls the
> > Complex overload of operator<<.

>
> Well it shouldn't. *You either have something else in your code you have
> overlooked, or there's a bug in your compiler. *Which compiler are you
> using?


I am using Visual Studio 2008. Here is a small compilable program
showing the issue:

#include <iostream>

class Complex
{
public:
Complex(float a, float b)
: real(a), imag(b)
{}

Complex operator+(const Complex& b)
{
return Complex(real+b.real, imag+b.imag);
}
/*
operator float()
{
return real;
}
*/
float real;
float imag;
};

std:stream& operator<<(std:stream& os, Complex& c)
{
os << "(" << c.real << ", " << c.imag << ")" << std::endl;

return os;
}

int main()
{
Complex c1(1.0f, 2.0f);
Complex c2(1.0f, 2.0f);

std::cout << c1 + c2 << std::endl;
}

Output: (2, 4)

If I uncomment the operator float(), and set a break point inside it,
it gets hit and the output is just 2 (the real part).



 
Reply With Quote
 
Ian Collins
Guest
Posts: n/a
 
      10-28-2010
On 10/28/10 05:10 PM, cronusf wrote:
>>>> Probably because the result of a+b is a temporary and you can't bind a
>>>> temporary to a non-const reference.

>>
>>> That's what I thought at first, but If
>>> I remove operator double() it behaves as expected and calls the
>>> Complex overload of operator<<.

>>
>> Well it shouldn't. You either have something else in your code you have
>> overlooked, or there's a bug in your compiler. Which compiler are you
>> using?

>
> I am using Visual Studio 2008. Here is a small compilable program
> showing the issue:
>
> #include<iostream>
>
> class Complex
> {
> public:
> Complex(float a, float b)
> : real(a), imag(b)
> {}
>
> Complex operator+(const Complex& b)
> {
> return Complex(real+b.real, imag+b.imag);
> }
> /*
> operator float()
> {
> return real;
> }
> */
> float real;
> float imag;
> };
>
> std:stream& operator<<(std:stream& os, Complex& c)
> {
> os<< "("<< c.real<< ", "<< c.imag<< ")"<< std::endl;
>
> return os;
> }
>
> int main()
> {
> Complex c1(1.0f, 2.0f);
> Complex c2(1.0f, 2.0f);
>
> std::cout<< c1 + c2<< std::endl;
> }
>
> Output: (2, 4)


That shouldn't compile. There isn't a suitable operator << for Complex.

--
Ian Collins
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
PSD to XHTML Conversion Services and PSD to HTML CSS ConversionServices, PSD to Joomla, Drupal, Wordpress Conversion xhtml champs Python 0 06-21-2011 11:59 AM
PSD to XHTML Conversion Services and PSD to HTML CSS ConversionServices, PSD to Joomla, Drupal, Wordpress Conversion PSD to XHTML Conversion Services and PSD to HTML CSS Conversion Services, PSD to Joomla, Drupal, Wor VHDL 0 04-25-2011 06:43 AM
conversion operator and conversion ctor subramanian100in@yahoo.com, India C++ 2 09-15-2009 12:46 PM
user defined conversion operator or operator overloading? hurcan solter C++ 3 08-29-2007 07:39 PM
<complex> : no match for 'operator*' // conversion operator double() Arvid Requate C++ 2 06-23-2006 10:41 AM



Advertisments