Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.c++ > #70267 > unrolled thread

Why enum is automatically converted in class member but not in global function

Started byJiiPee <no@notvalid.com>
First post2019-12-05 00:53 +0000
Last post2019-12-05 14:21 +0000
Articles 3 — 2 participants

Back to article view | Back to comp.lang.c++


Contents

  Why enum is automatically converted in class member but not in global function JiiPee <no@notvalid.com> - 2019-12-05 00:53 +0000
    Re: Why enum is automatically converted in class member but not in global function Bo Persson <bo@bo-persson.se> - 2019-12-05 02:57 +0100
      Re: Why enum is automatically converted in class member but not in global function JiiPee <no@notvalid.com> - 2019-12-05 14:21 +0000

#70267 — Why enum is automatically converted in class member but not in global function

FromJiiPee <no@notvalid.com>
Date2019-12-05 00:53 +0000
SubjectWhy enum is automatically converted in class member but not in global function
Message-ID<9yYFF.431219$TS1.19885@fx09.am4>
I wonder why the compiler does automatic type conversion for an enum to 
int if the function is a class member, but does not do that if the 
function is a global function.

Example code:

enum MyEnum
{
enumVal1
}


1)
+= as a class member:

template <typename T>
inline void MyClass<T>::operator += (const T& val)
{
}

MyClass<int> obj;
obj += enumVal1; // converts enumVal1 to int and calls operator +=

This all works.

2)

The same += as a global function:

template <typename T>
inline void operator += (const MyClass<T>& obj, const T& val)
{
}

obj += enumVal1; // does not convert enumVal1 to int

This one does not compile, I get this error:
"+= does not define this operator or a conversion to a type acceptable 
to the predefined operator"

[toc] | [next] | [standalone]


#70269

FromBo Persson <bo@bo-persson.se>
Date2019-12-05 02:57 +0100
Message-ID<h4r6fdFtv00U1@mid.individual.net>
In reply to#70267
On 2019-12-05 at 01:53, JiiPee wrote:
> I wonder why the compiler does automatic type conversion for an enum to 
> int if the function is a class member, but does not do that if the 
> function is a global function.
> 
> Example code:
> 
> enum MyEnum
> {
> enumVal1
> }
> 
> 
> 1)
> += as a class member:
> 
> template <typename T>
> inline void MyClass<T>::operator += (const T& val)
> {
> }
> 
> MyClass<int> obj;
> obj += enumVal1; // converts enumVal1 to int and calls operator +=
> 
> This all works.
> 
> 2)
> 
> The same += as a global function:
> 
> template <typename T>
> inline void operator += (const MyClass<T>& obj, const T& val)
> {
> }
> 
> obj += enumVal1; // does not convert enumVal1 to int
> 
> This one does not compile, I get this error:
> "+= does not define this operator or a conversion to a type acceptable 
> to the predefined operator"
> 
> 

It has to do with the order of type deduction and overload resolution. 
Type deduction is always performed first.

In the first case, T is given from the use of MyClass<int>. That class 
instantiation has a member operator that takes an int, and the enum is 
convertible to int. Good.


In the second case, the compiler is looking for an operator that takes a 
class object and an enum value. There isn't any.

The fact that the enum might be convertible to some other type that 
would match the template doesn't help, as type deduction is performed 
first and enumVal1 just isn't a T. So that template is not added to the 
potential overload set.



     Bo Persson

[toc] | [prev] | [next] | [standalone]


#70281

FromJiiPee <no@notvalid.com>
Date2019-12-05 14:21 +0000
Message-ID<gn8GF.229352$ae.164202@fx33.am4>
In reply to#70269
On 05/12/2019 01:57, Bo Persson wrote:
> On 2019-12-05 at 01:53, JiiPee wrote:
>> I wonder why the compiler does automatic type conversion for an enum 
>> to int if the function is a class member, but does not do that if the 
>> function is a global function.
>>
>> Example code:
>>
>> enum MyEnum
>> {
>> enumVal1
>> }
>>
>>
>> 1)
>> += as a class member:
>>
>> template <typename T>
>> inline void MyClass<T>::operator += (const T& val)
>> {
>> }
>>
>> MyClass<int> obj;
>> obj += enumVal1; // converts enumVal1 to int and calls operator +=
>>
>> This all works.
>>
>> 2)
>>
>> The same += as a global function:
>>
>> template <typename T>
>> inline void operator += (const MyClass<T>& obj, const T& val)
>> {
>> }
>>
>> obj += enumVal1; // does not convert enumVal1 to int
>>
>> This one does not compile, I get this error:
>> "+= does not define this operator or a conversion to a type 
>> acceptable to the predefined operator"
>>
>>
>
> It has to do with the order of type deduction and overload resolution. 
> Type deduction is always performed first.
>
> In the first case, T is given from the use of MyClass<int>. That class 
> instantiation has a member operator that takes an int, and the enum is 
> convertible to int. Good.
>
>
> In the second case, the compiler is looking for an operator that takes 
> a class object and an enum value. There isn't any.
>
> The fact that the enum might be convertible to some other type that 
> would match the template doesn't help, as type deduction is performed 
> first and enumVal1 just isn't a T. So that template is not added to 
> the potential overload set.
>
>

ok, thanks. A little difficult to google these issues, thats why asked 
here :)

[toc] | [prev] | [standalone]


Back to top | Article view | comp.lang.c++


csiph-web