Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > Is this using-declaration ill-formed?

Reply
Thread Tools

Is this using-declaration ill-formed?

 
 
Johannes Schaub (litb)
Guest
Posts: n/a
 
      08-16-2010
14.5.2/7: "A using-declaration in a derived class cannot refer to a
specialization of a template conversion function in a base class."

Does this make the following code ill-formed?

struct A {
template<typename T> operator T();
operator int();
};

struct B : A { using A:perator int; };

 
Reply With Quote
 
 
 
 
Johannes Schaub (litb)
Guest
Posts: n/a
 
      08-16-2010
Johannes Schaub (litb) wrote:

> 14.5.2/7: "A using-declaration in a derived class cannot refer to a
> specialization of a template conversion function in a base class."
>
> Does this make the following code ill-formed?
>
> struct A {
> template<typename T> operator T();
> operator int();
> };
>
> struct B : A { using A:perator int; };


There are two interpretations of this:

- If the use of the name in a using declaration results in refering to the
specialization of a template conversion function, or results in an overload
set that includes such a specialization, the program is ill-formed because a
using-declaration cannot refer to such a function.

- To determine the meaning of the name used in a using declaration, template
conversion functions are ignored, because a using declaration cannot refer
to a specialization of it, nor (in c++03) to the template itself.

Both interpretation look viable to me. The note at 7.3.3/4 indicates that
the second option is taken (and my code would be wellformed then), but is
there a normative ground for that interpretation - maybe an inherent implied
meaning of "cannot" in international standards?

By purely taking the normative wording, both options look roughly equally
viable to me, and the first looks even a bit more viable.
 
Reply With Quote
 
 
 
 
Johannes Schaub (litb)
Guest
Posts: n/a
 
      08-16-2010
Johannes Schaub (litb) wrote:

> Johannes Schaub (litb) wrote:
>
>> 14.5.2/7: "A using-declaration in a derived class cannot refer to a
>> specialization of a template conversion function in a base class."
>>
>> Does this make the following code ill-formed?
>>
>> struct A {
>> template<typename T> operator T();
>> operator int();
>> };
>>
>> struct B : A { using A:perator int; };

>
> There are two interpretations of this:
>
> - If the use of the name in a using declaration results in refering to the
> specialization of a template conversion function, or results in an
> overload set that includes such a specialization, the program is
> ill-formed because a using-declaration cannot refer to such a function.
>
> - To determine the meaning of the name used in a using declaration,
> template conversion functions are ignored, because a using declaration
> cannot refer to a specialization of it, nor (in c++03) to the template
> itself.
>


I should correct: You can refer to the template itself in C++03 too, but it
makes rather little sense to write such a conversion function where you can:

struct A { template<typename T> operator int(); };
struct B : A { using A:perator int; };

Valid, but since "T" is nondeduced, the utility of it is very doubtly. C++0x
allows for it to have a default argument...
 
Reply With Quote
 
Gil
Guest
Posts: n/a
 
      08-16-2010
I believe your code is ill formed.
to me 14.5.2/7 is just a clarification of a special case of 7.3.3/5.

struct B : A { using A:perator _no_name_<int>; } //ill formed
7.3.3/5

so my interpretation is 14.5.2/7 should be moved to 7.3.3/5 explaining
that specialization of conversion operators are still considered
template-id _as_if they would have a name.

as I see it, the fact that specializations of member templates for
conversion functions are not found by name lookup is a totally
different issue, unrelated to 14.5.2/7. that's why the note about it
in 7.3.3/4 looks misplaced to me.
 
Reply With Quote
 
Johannes Schaub (litb)
Guest
Posts: n/a
 
      08-16-2010
Johannes Schaub (litb) wrote:

> Johannes Schaub (litb) wrote:
>
>> 14.5.2/7: "A using-declaration in a derived class cannot refer to a
>> specialization of a template conversion function in a base class."
>>
>> Does this make the following code ill-formed?
>>
>> struct A {
>> template<typename T> operator T();
>> operator int();
>> };
>>
>> struct B : A { using A:perator int; };

>
> There are two interpretations of this:
>
> - If the use of the name in a using declaration results in refering to the
> specialization of a template conversion function, or results in an
> overload set that includes such a specialization, the program is
> ill-formed because a using-declaration cannot refer to such a function.
>
> - To determine the meaning of the name used in a using declaration,
> template conversion functions are ignored, because a using declaration
> cannot refer to a specialization of it, nor (in c++03) to the template
> itself.
>


I guess i'm too fast with pressing "send" with non-moderated groups Here
is what i sent to comp.std.c++, which is more what i meant to write. Please
forgive my many follow-self-answers. I'm really a bloody usenet-
nonmoderated-groups starter:

##################################

I see two interpretations:

Option 1:
----------

- During determining the meaning of the name, argument deduction for
template conversion functions is not done and only template conversion
functions or non-specialization conversion functions are found:

struct A {
template<typename T> operator int(); // #1
template<typename T> operator T(); // #2
operator int(); // #3
};

struct B : A {
// only specifies the name of #1 and #3
using A:perator int;
};

Option 2:
----------

- After determining the meaning of the name, if the name refers to a
template conversion function specialization, the program is ill-formed.

struct A {
template<typename T> operator int(); // #1
template<typename T> operator T(); // #2
operator int(); // #3
};

struct B : A {
// ill-formed, because it refers to a specialization of #2.
using A:perator int;
};

------------------------

Subsequently, i found a note in 7.3.3/4 which indicates the first option is
taken:

"Since specializations of member templates for conversion functions are not
found by name lookup, they are not considered when a using-declaration
specifies a conversion function"

This says what the intent of the standard is, and sort of answers my
question i think. If anyone knows normative wording for it, i would still
like to read about it, though.

 
Reply With Quote
 
Gennaro Prota
Guest
Posts: n/a
 
      08-16-2010
On 16/08/2010 21.26, Johannes Schaub (litb) wrote:
> Johannes Schaub (litb) wrote:
>
>> Johannes Schaub (litb) wrote:
>>
>>> 14.5.2/7: "A using-declaration in a derived class cannot refer to a
>>> specialization of a template conversion function in a base class."
>>>
>>> Does this make the following code ill-formed?
>>>
>>> struct A {
>>> template<typename T> operator T();
>>> operator int();
>>> };
>>>
>>> struct B : A { using A:perator int; };

>>
>> There are two interpretations of this:
>>
>> - If the use of the name in a using declaration results in refering to the
>> specialization of a template conversion function, or results in an
>> overload set that includes such a specialization, the program is
>> ill-formed because a using-declaration cannot refer to such a function.
>>
>> - To determine the meaning of the name used in a using declaration,
>> template conversion functions are ignored, because a using declaration
>> cannot refer to a specialization of it, nor (in c++03) to the template
>> itself.
>>

>
> I should correct: You can refer to the template itself in C++03 too, but it
> makes rather little sense to write such a conversion function where you can:
>
> struct A { template<typename T> operator int(); };
> struct B : A { using A:perator int; };
>
> Valid, but since "T" is nondeduced, the utility of it is very doubtly. C++0x
> allows for it to have a default argument...


I haven't checked the standard as thoroughly as this question
would require but, yes, *off-hand* I'd have expected that if the
intended meaning was 1 (first bullet above) they would have used
"shall" or "shall not". Whereas "cannot" is, by strict ISO rules
(see e.g.

<http://anubis.dkuug.dk/JTC1/SC22/WG9/isodir3.pdf>

) to be taken as "there is no possibility of".

But...

a) One wonders what's the point of a "there's no possibility of"
/outside of an explicative note/ if it follows from other
normative parts (if it doesn't follow, then why not using
"shall" or "shall not"?). Where are such normative parts in this
case?

b) Not all people who write the C++ standard seem to be aware of
these (IMHO very fastidious and unsuited) rules. I've certainly
found usages of "may not" to where a prohibition was meant, for
instance (an example from memory: the prohibition to replace the
placement forms of operator new), although the document linked
to above doesn't allow it.

--
Gennaro Prota | name.surname yahoo.com
Breeze C++ (preview): <https://sourceforge.net/projects/breeze/>
Do you need expertise in C++? I'm available.
 
Reply With Quote
 
James Kanze
Guest
Posts: n/a
 
      08-17-2010
On Aug 16, 9:02 pm, "Johannes Schaub (litb)" <(E-Mail Removed)>
wrote:
> Johannes Schaub (litb) wrote:
> > Johannes Schaub (litb) wrote:


> >> 14.5.2/7: "A using-declaration in a derived class cannot
> >> refer to a specialization of a template conversion function
> >> in a base class."


> >> Does this make the following code ill-formed?


> >> struct A {
> >> template<typename T> operator T();
> >> operator int();
> >> };


> >> struct B : A { using A:perator int; };


> > There are two interpretations of this:


> > - If the use of the name in a using declaration results in
> > refering to the specialization of a template conversion
> > function, or results in an overload set that includes such
> > a specialization, the program is ill-formed because
> > a using-declaration cannot refer to such a function.


> > - To determine the meaning of the name used in a using
> > declaration, template conversion functions are ignored,
> > because a using declaration cannot refer to a specialization
> > of it, nor (in c++03) to the template itself.


> I guess i'm too fast with pressing "send" with non-moderated
> groups Here is what i sent to comp.std.c++, which is more
> what i meant to write. Please forgive my many
> follow-self-answers. I'm really a bloody usenet-
> nonmoderated-groups starter:


> ##################################


> I see two interpretations:


> Option 1:
> ----------


> - During determining the meaning of the name, argument deduction for
> template conversion functions is not done and only template conversion
> functions or non-specialization conversion functions are found:


> struct A {
> template<typename T> operator int(); // #1
> template<typename T> operator T(); // #2
> operator int(); // #3


Note that these are three, unrelated overloaded functions.

> };


> struct B : A {
> // only specifies the name of #1 and #3
> using A:perator int;


According to my understanding of what you've posted, #1 will not
be found, and this only specified #3.

Note that #1 requires very special syntax to be used anyway.
Since there is nothing in the declaration which depends on the
template type, type deduction will always fail on it, and the
only way to call it is:
int x = anA.operator int<SomeType>();

> };


> Option 2:
> ----------


> - After determining the meaning of the name, if the name refers to a
> template conversion function specialization, the program is ill-formed.


> struct A {
> template<typename T> operator int(); // #1
> template<typename T> operator T(); // #2
> operator int(); // #3
> };


> struct B : A {
> // ill-formed, because it refers to a specialization of #2.
> using A:perator int;


Not ill-formed, because it refers to #3.

> };


> ------------------------


> Subsequently, i found a note in 7.3.3/4 which indicates the
> first option is taken:


> "Since specializations of member templates for conversion
> functions are not found by name lookup, they are not
> considered when a using-declaration specifies a conversion
> function"


> This says what the intent of the standard is, and sort of
> answers my question i think. If anyone knows normative wording
> for it, i would still like to read about it, though.


I'm still trying to understand the question. But one thing is
certain:
int x = anA;
will, without any further qualifications, invoke #3. And this
is what I would intuitively expect using A:perator int to
refer to.

--
James Kanze
 
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




Advertisments