Topic: Is "~typedef_name()" legal?
Author: fjh@munta.cs.mu.OZ.AU (Fergus Henderson)
Date: 1995/06/17 Raw View
kanze@lts.sel.alcatel.de (James Kanze US/ESC 60/3/141 #40763) writes:
>clamage@Eng.Sun.COM (Steve Clamage) writes:
>
>|> > typedef A B; // synonym;
>|> > ...
>|> > B b;
>|> > b.~B(); // legal?
Yes.
>|> No. From 7.1.3, "The typedef specifier":
>
>|> "A typedef name that names a class is a class name (9.1). The typedef name
>|> shall not be used after a class, struct, or union prefix and not in the names
>|> for constructors and destructors within the class declaration itself."
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The use in the example is fine, since it is not "within the class
declaration itself". Of course, this raises the question: is the
following code supposed to be ill-formed? I very much doubt that was the
intent, but the words in the draft seem to say so.
class A {
typedef A Self;
inline void foo(Self *p) {
p->~Self; // error, because this is
// within the class declaration
}
inline void bar(Self *p);
};
inline void A::bar(Self *p) {
p->~Self; // ok, because this is not
// within the class declaration
}
>Does this mean that some of the following will fail?
No.
> class MyClass {} ;
> typedef int T1 ;
> typedef MyClass T2 ;
>
> vector< T1 > a ; // OK?
> vector< T2 > b ; // OK?
They're both OK.
--
Fergus Henderson
fjh@cs.mu.oz.au
http://www.cs.mu.oz.au/~fjh
Author: bmcphers@alias.com (Brent McPherson)
Date: 1995/06/07 Raw View
In article <3qgbfl$1tq@engnews2.Eng.Sun.COM> clamage@Eng.Sun.COM (Steve Clamage) writes:
From: clamage@Eng.Sun.COM (Steve Clamage)
Newsgroups: comp.std.c++
Date: 30 May 1995 23:58:45 GMT
Organization: Sun Microsystems Inc.
Reply-To: clamage@Eng.Sun.COM
In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni) writes:
>One cfront-ism that our compiler had difficulties with is the following:
>
> class A {
> public:
> A() {}
> ~A() {}
> };
>
> typedef A B; // synonym;
>
> ...
> B b;
> b.~B(); // legal?
No. From 7.1.3, "The typedef specifier":
"A typedef name that names a class is a class name (9.1). The typedef name
shall not be used after a class, struct, or union prefix and not in the names
for constructors and destructors within the class declaration itself."
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The ARM did not say whether the code above should be allowed, but the
standard is now clear.
I do not agree with that statement since the destructor call is *not*
"within the class declaration".
Furthermore, I think it is *unorthogonal* not to allow the above construct.
For example, all the following are legal constructs:
B b1; // declaration
B * b2 = new B; // instantiation (constructor explicitly called!)
B * b3 = (B *)&b1; // typecast
b1.B::foo(); // call of method of B
so it seems unorthogonal *not* to allow B to be used to call a destructor
when it can be used to call a constructor!
[Note: The last construct is also used in the old 'typedef SomeBaseClass Parent;'
hack that allows 'Parent::method();' to be used in a derived class in order
to minimize coupling between base classes and derived classes.]
Author: kanze@lts.sel.alcatel.de (James Kanze US/ESC 60/3/141 #40763)
Date: 1995/06/01 Raw View
In article <3qi5uk$32j@fido.asd.sgi.com> jfw@mortmere.engr.sgi.com
(John Wilkinson) writes:
|> In article <sdouglass-3105951430020001@193.131.176.202>,
|> sdouglass@armltd.co.uk (scott douglass) writes:
|> |> In article <3qgbfl$1tq@engnews2.Eng.Sun.COM>, clamage@Eng.Sun.COM
|> |> wrote:
|> |>
|> |> : In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni)
|> |> writes:
|> |> : >One cfront-ism that our compiler had difficulties with is the
|> |> following:
|> |> : >
|> |> : > class A {
|> |> : > public:
|> |> : > A() {}
|> |> : > ~A() {}
|> |> : > };
|> |> : >
|> |> : > typedef A B; // synonym;
|> |> : >
|> |> : > ...
|> |> : > B b;
|> |> : > b.~B(); // legal?
|> |> :
|> |> : No. From 7.1.3, "The typedef specifier":
|> |> :
|> |> : "A typedef name that names a class is a class name (9.1). The
|> |> typedef name
|> |> : shall not be used after a class, struct, or union prefix and not in
|> |> the names
|> |> : for constructors and destructors within the class declaration
|> |> itself."
|> |>
|> |> I disagree. The usage 'b.~B()' above is not "within the class
|> |> declaration
|> |> itself". I think the above usage is legal. The following, however, is
|> |> specifically disallowed:
|> |>
|> |> class X;
|> |> typedef X T;
|> |> class X {
|> |> T(); // illegal
|> |> ~T(); // illegal
|> |> };
|> I agree that the citation from 7.1.3 does not apply, but I still think the
|> usage
|> described is illegal. According to 12.4:
|> "A member function of a class cl named ~cl is called a destructor."
|> Declaring typedef cl CL does not make ~CL a synonym for ~cl any more than
|> it
|> makes "operator CL" a synonym for "operator cl".
Except that `operator CL' *is* a synonym for `operator cl'. Or???
--
James Kanze Tel.: (+33) 88 14 49 00 email: kanze@gabi-soft.fr
GABI Software, Sarl., 8 rue des Francs-Bourgeois, F-67000 Strasbourg, France
Conseils en informatique industrielle --
-- Beratung in industrieller Datenverarbeitung
Author: shankar@sgi.com (Shankar Unni)
Date: 1995/05/30 Raw View
One cfront-ism that our compiler had difficulties with is the following:
class A {
public:
A() {}
~A() {}
};
typedef A B; // synonym;
...
B b;
b.~B(); // legal?
I.e. I guess my question is: what exactly does "~A()" mean when you declare
it in class A? Is it the literal name of a function, or is it a sort of
operator which should be able to take any synonym of A after it?
--
Shankar Unni E-Mail: shankar@sgi.com
Silicon Graphics Inc. Phone: +1-415-390-2072
URL: http://reality.sgi.com/employees/shankar
Author: clamage@Eng.Sun.COM (Steve Clamage)
Date: 1995/05/30 Raw View
In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni) writes:
>One cfront-ism that our compiler had difficulties with is the following:
>
> class A {
> public:
> A() {}
> ~A() {}
> };
>
> typedef A B; // synonym;
>
> ...
> B b;
> b.~B(); // legal?
No. From 7.1.3, "The typedef specifier":
"A typedef name that names a class is a class name (9.1). The typedef name
shall not be used after a class, struct, or union prefix and not in the names
for constructors and destructors within the class declaration itself."
The ARM did not say whether the code above should be allowed, but the
standard is now clear.
---
Steve Clamage, stephen.clamage@eng.sun.com
Author: kanze@lts.sel.alcatel.de (James Kanze US/ESC 60/3/141 #40763)
Date: 1995/05/31 Raw View
In article <3qgbfl$1tq@engnews2.Eng.Sun.COM> clamage@Eng.Sun.COM
(Steve Clamage) writes:
|> In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni) writes:
|> >One cfront-ism that our compiler had difficulties with is the following:
|> >
|> > class A {
|> > public:
|> > A() {}
|> > ~A() {}
|> > };
|> >
|> > typedef A B; // synonym;
|> >
|> > ...
|> > B b;
|> > b.~B(); // legal?
|> No. From 7.1.3, "The typedef specifier":
|> "A typedef name that names a class is a class name (9.1). The typedef name
|> shall not be used after a class, struct, or union prefix and not in the names
|> for constructors and destructors within the class declaration itself."
|> The ARM did not say whether the code above should be allowed, but the
|> standard is now clear.
Does this mean that some of the following will fail?
class MyClass {} ;
typedef int T1 ;
typedef MyClass T2 ;
vector< T1 > a ; // OK?
vector< T2 > b ; // OK?
It is my understanding that the code for the standard vector normally
allocates raw memory, and uses placement new and explicit destructor
calls to construct/destruct the objects. (Note that things like
`p->~int()' are explicitly allowed. What about `p->~char*()'?)
Also: I'm not sure I generally know when a typename was defined by a
typedef. Consider the following (a vector of iterators):
vector< vector< int >::iterator >
c ;
Surely making this illegal is partially castrating STL. But I suspect
that in many cases, `vector< int >::iterator' is a typedef (maybe for
int*).
--
James Kanze Tel.: (+33) 88 14 49 00 email: kanze@gabi-soft.fr
GABI Software, Sarl., 8 rue des Francs-Bourgeois, F-67000 Strasbourg, France
Conseils en informatique industrielle --
-- Beratung in industrieller Datenverarbeitung
Author: sdouglass@armltd.co.uk (scott douglass)
Date: 1995/05/31 Raw View
In article <3qgbfl$1tq@engnews2.Eng.Sun.COM>, clamage@Eng.Sun.COM wrote:
: In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni) writes:
: >One cfront-ism that our compiler had difficulties with is the following:
: >
: > class A {
: > public:
: > A() {}
: > ~A() {}
: > };
: >
: > typedef A B; // synonym;
: >
: > ...
: > B b;
: > b.~B(); // legal?
:
: No. From 7.1.3, "The typedef specifier":
:
: "A typedef name that names a class is a class name (9.1). The typedef name
: shall not be used after a class, struct, or union prefix and not in the names
: for constructors and destructors within the class declaration itself."
I disagree. The usage 'b.~B()' above is not "within the class declaration
itself". I think the above usage is legal. The following, however, is
specifically disallowed:
class X;
typedef X T;
class X {
T(); // illegal
~T(); // illegal
};
--scott
Author: jfw@mortmere.engr.sgi.com (John Wilkinson)
Date: 1995/05/31 Raw View
In article <sdouglass-3105951430020001@193.131.176.202>,
sdouglass@armltd.co.uk (scott douglass) writes:
|> In article <3qgbfl$1tq@engnews2.Eng.Sun.COM>, clamage@Eng.Sun.COM
|> wrote:
|>
|> : In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni)
|> writes:
|> : >One cfront-ism that our compiler had difficulties with is the
|> following:
|> : >
|> : > class A {
|> : > public:
|> : > A() {}
|> : > ~A() {}
|> : > };
|> : >
|> : > typedef A B; // synonym;
|> : >
|> : > ...
|> : > B b;
|> : > b.~B(); // legal?
|> :
|> : No. From 7.1.3, "The typedef specifier":
|> :
|> : "A typedef name that names a class is a class name (9.1). The
|> typedef name
|> : shall not be used after a class, struct, or union prefix and not in
|> the names
|> : for constructors and destructors within the class declaration
|> itself."
|>
|> I disagree. The usage 'b.~B()' above is not "within the class
|> declaration
|> itself". I think the above usage is legal. The following, however, is
|> specifically disallowed:
|>
|> class X;
|> typedef X T;
|> class X {
|> T(); // illegal
|> ~T(); // illegal
|> };
I agree that the citation from 7.1.3 does not apply, but I still think the
usage
described is illegal. According to 12.4:
"A member function of a class cl named ~cl is called a destructor."
Declaring typedef cl CL does not make ~CL a synonym for ~cl any more than
it
makes "operator CL" a synonym for "operator cl".
Author: clamage@Eng.Sun.COM (Steve Clamage)
Date: 1995/05/31 Raw View
In article 3105951430020001@193.131.176.202, sdouglass@armltd.co.uk (scott douglass) writes:
>In article <3qgbfl$1tq@engnews2.Eng.Sun.COM>, clamage@Eng.Sun.COM wrote:
>
>: In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni) writes:
>: >One cfront-ism that our compiler had difficulties with is the following:
>: >
>: > class A {
>: > public:
>: > A() {}
>: > ~A() {}
>: > };
>: >
>: > typedef A B; // synonym;
>: >
>: > ...
>: > B b;
>: > b.~B(); // legal?
>:
>: No. From 7.1.3, "The typedef specifier":
>:
>: "A typedef name that names a class is a class name (9.1). The typedef name
>: shall not be used after a class, struct, or union prefix and not in the names
>: for constructors and destructors within the class declaration itself."
>
>I disagree. The usage 'b.~B()' above is not "within the class declaration
>itself". I think the above usage is legal.
I managed to garble my post quoted above (and I apologize for the garbage
characters that it contained). I also meant to include the following paragraph:
"12.4 Destructors
A member function of class cl named ~cl is called a destructor; it is
used to destroy objects of type cl."
It seems to me that if you put these together it is pretty clear you
can't use a typedef name for the name of a destructor. (You can use it
for the name of the class, however.)
In fact, I was pretty sure that was the deliberate intent of the committee.
I have since been told that the subject is still under some discussion.
This is a good example of a "corner" in the language, where compilers may
differ no matter what the state of the current draft standard, and where
compilers may continue to differ for some time after the standard is final.
It's best to write code that doesn't depend on any particular interpretation;
use only the class name for the name of a destructor.
---
Steve Clamage, stephen.clamage@eng.sun.com
Author: evan@hplerk.hpl.hp.com (Evan Kirshenbaum)
Date: 1995/05/31 Raw View
In article <3qgbfl$1tq@engnews2.eng.sun.com>,
Steve Clamage <clamage@Eng.Sun.COM> wrote:
>In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni) writes:
>>One cfront-ism that our compiler had difficulties with is the following:
>>
>> class A {
>> public:
>> A() {}
>> ~A() {}
>> };
>>
>> typedef A B; // synonym;
>>
>> ...
>> B b;
>> b.~B(); // legal?
>
>No. From 7.1.3, "The typedef specifier":
>
>"A typedef name that names a class is a class name (9.1). The typedef name
>shall not be used after a class, struct, or union prefix and not in the names
>for constructors and destructors within the class declaration itself."
>
>The ARM did not say whether the code above should be allowed, but the
>standard is now clear.
Actually, I believe that it is fine. The passage you quoted says
"within the class declaration itself", which this is not. In fact,
the example that follows that passage says
typedef struct S T;
S a = T(); // ok
which implies to me that *outside of the declaration* the typedef name
can be used in an explicit constructor. I would assume that explicit
destructor (outside of the declaration) would be fine as well.
Evan Kirshenbaum +------------------------------------
HP Laboratories | People think it must be fun to be a
1500 Page Mill Road, Building 4A | super genius, but they don't
Palo Alto, CA 94304 | realize how hard it is to put up
| with all the idiots in the world.
kirshenbaum@hpl.hp.com | Calvin
(415)857-7572
Author: jdp@polstra.com (John Polstra)
Date: 1995/05/31 Raw View
In article <3qgbfl$1tq@engnews2.Eng.Sun.COM>,
Steve Clamage <clamage@Eng.Sun.COM> wrote:
> In article kfl@fido.asd.sgi.com, shankar@sgi.com (Shankar Unni) writes:
> >
> > class A {
> > public:
> > A() {}
> > ~A() {}
> > };
> >
> > typedef A B; // synonym;
> >
> > ...
> > B b;
> > b.~B(); // legal?
>
> No. From 7.1.3, "The typedef specifier":
>
> "A typedef-name that names a class is a class-name (9.1). The typedef-name
> shall not be used after a class, struct, or union prefix and not in the names
> for constructors and destructors within the class declaration itself."
I can't agree with your interpretation here. The restriction "and
not in the names for constructors and destructors within the class
declaration itself" does not apply, because the statement in question
does not appear within the class declaration itself.
Furthermore, the WP goes on to give an example in which the typedef name
is used (legally) as the name for the constructor. In the present
context, the WP's example is analogous to this:
A a = B(); // ok
The wording of "... for constructors and destructors ..." would seem to
imply that constructors and destructors are to be treated the same.
Finally, if "b.~B()" were illegal, that would cause needless problems
for templates that made explicit destructor calls. The WP states that
"T::~T()" is legal even when T is a built-in type such as int. Your
interpretation concerning typedef names would make typedefs the *only*
case for which explicit destructor calls could not be used. Surely that
cannot be the intent of the committee.
My interpretation of the draft WP is that the statement in question is legal.
--
John Polstra jdp@polstra.com
John D. Polstra & Co., Inc. Seattle, Washington USA
"Self-knowledge is always bad news." -- John Barth