typedef, member function and const meat different compilers

J

joe

hi,
after reading some articles and faq,
i want to clarify myself what's correct(conform to standard) and
what's not?
or what should be correct but it isn't simply because compilers don't
support.
(first i compiled them with g++3.x. ERR means compiler will bark,
otherwise it does accept it. Then the Comeau C/C++ 4.3.3 comes)



//Q1===================================================//
--g++
typedef const int G(); //cv-qualified to int
typedef int F(); //function type

typedef const F H; //ERR, qualifier applied to function type means
nothing
typedef F const H; //what's it really? i don't know, but compiled with
g++

--Comeau
"ComeauTest.c", line 1: warning: type qualifier on return type is
meaningless
typedef const int G();
//well, different to what i think. what does std says?
^

"ComeauTest.c", line 3: warning: type qualifiers on function types are
ignored
typedef const F H;
^

"ComeauTest.c", line 4: warning: type qualifiers on function types are
ignored
typedef F const H;
^

In strict mode, with -tused, Compile succeeded





//Q2====================================================//
--g++
typedef int (*F2)(); //ok, function pointer "int (*)()"

the following two will be compiled by g++,
but i think they are trivial(or, they shouldn't be compiled?)
typedef const F2 H2; //qualifier applied to function pointer?
typedef F2 const H3; //like the above

--Comeau
In strict mode, with -tused, Compile succeeded



//Q3=======================================================//
--g++
class C;
typedef int (C::*I)(); //a type of "int (C::*)()"
typedef int (C::*J)() const; //const member func, a type of "int
(C::*)() const"

typedef int (C::K)(); //ERR, typedef names can't be class qualified
well, seems reasonable to be ERR, but why?

--Comeau
"ComeauTest.c", line 4: error: qualified name is not allowed
typedef int (C::K)();
^

1 error detected in the compilation of "ComeauTest.c".

In strict mode, with -tused, Compile failed



//Q4==================================================//
--g++
compiled ok, but should they be compiled ok?
class C;
typedef int Q();
typedef Q const C::* R1; //cv-qualified ptr?
typedef Q C::* const R2; //like the above

//--Comeau
"ComeauTest.c", line 3: warning: type qualifiers on function types are
ignored
typedef Q const C::* R1;
^


In strict mode, with -tused, Compile succeeded



//Q5======================================================//
--g++
typedef int M() const; //ERR, invalid qualifier for non-member func
type
why? doesn't it implicitly expresses "int (someclass::*M)() const" and
let us do
the following:

class A
{
M mf;
};

--Comeau
In strict mode, with -tused, Compile succeeded


//Q6=====================================================//
--g++
class C
{
typedef int C::M3() const;
typedef int M2() const; //ERR
in a class can't we get things done like above?
};

--Comeau
"ComeauTest.c", line 3: error: qualified name is not allowed in member
declaration
typedef int C::M3() const;
^
//well, different to what i think. what does std says?

1 error detected in the compilation of "ComeauTest.c".

In strict mode, with -tused, Compile failed





i know, it'll be unnecessary and complecated to do things like them
above.
but i will really thank for anyone who give me some hints.
thanks.


sincerely
ianz
 
M

Michiel Salters

hi,
after reading some articles and faq,
i want to clarify myself what's correct(conform to standard) and
what's not? or what should be correct but it isn't simply
because compilers don't support.
(first i compiled them with g++3.x. ERR means compiler will bark,
otherwise it does accept it. Then the Comeau C/C++ 4.3.3 comes)


//Q1===================================================//
--g++
typedef const int G(); //cv-qualified to int
typedef int F(); //function type

typedef const F H; //ERR, qualifier applied to function type means
nothing
typedef F const H; //what's it really? i don't know, but compiled with
g++

F const equals const F, so g++ should complain on both.
--Comeau
"ComeauTest.c", line 1: warning: type qualifier on return type is
meaningless
typedef const int G();
//well, different to what i think. what does std says?
^

Comeau is correct. The situation would be different when returning
a type with member functions. Basically, the int returned is a
temporary which must be copied before it can be used. Since copying
a const int doesn't differ from copying a non-const, the warning
is good - it points out something you didn't know.
"ComeauTest.c", line 3: warning: type qualifiers on function types are
ignored
typedef const F H;
^
"ComeauTest.c", line 4: warning: type qualifiers on function types are
ignored
typedef F const H;
^

Sure, the code is wrong, but the only restriction the standard imposes
is that the compiler must warn you. If it can continue, it is allowed to,
but it doesn't have to.
//Q2====================================================//
--g++
typedef int (*F2)(); //ok, function pointer "int (*)()"

the following two will be compiled by g++,
but i think they are trivial(or, they shouldn't be compiled?)
typedef const F2 H2; //qualifier applied to function pointer?
typedef F2 const H3; //like the above

Sure. You can't modify a function, but you definitely can modify
a function pointer. Therefore, const qualifying a function
doesn't make sense, but const-qualifying a function pointer does.
Both H2 and H3 decalre function pointers that must be initialized
on declararation, and keep pointing to that same function during
their lifetimes.
//Q3=======================================================//
--g++
class C;
typedef int (C::*I)(); //a type of "int (C::*)()"
typedef int (C::*J)() const; //const member func, a type of "int
(C::*)() const"

typedef int (C::K)(); //ERR, typedef names can't be class qualified
well, seems reasonable to be ERR, but why?

I and J are member pointers, but there is no type int(C::)().
Therefore, you can't typedef K to that.
//Q4==================================================//
--g++
compiled ok, but should they be compiled ok?
class C;
typedef int Q();
typedef Q const C::* R1; //cv-qualified ptr?
typedef Q C::* const R2; //like the above

No, read from R1 out. R1 is a pointer to member of C, and the member
has type Q const (which is ill-formed, Q is a function type)
Similar, R2 is a const pointer to member of C, and the member has
type Q.

Objects of type R1 can be changed, but cannot change what they point to
( except that Q const is ill formed).
Objects of type R2 cannot be changed, but can change what they point to
( except that you can't change functions )

//--Comeau
"ComeauTest.c", line 3: warning: type qualifiers on function types are
ignored
typedef Q const C::* R1;

Again, warning and then ignoring is a legal error handling strategy.
//Q5======================================================//
--g++
typedef int M() const;
ERR, invalid qualifier for non-member func type
why? doesn't it implicitly expresses "int (someclass::*M)() const"
and let us do the following:

class A
{
M mf;
};

No, not at all. M almost denotes a function type, but the const
doesn't make sense. What modification would it prevent?
Certainly a pointer to member is different from a function (the first
can be a simple numer, e.g. the third function in the vtable),
so you couldn't use it as a generic function pointer anyway.
//Q6=====================================================//
--g++
class C
{
typedef int C::M3() const;
typedef int M2() const; //ERR
in a class can't we get things done like above?
};

No, because 'int ()' is the type of a free function, even if written
within a class.
--Comeau
"ComeauTest.c", line 3: error: qualified name is not allowed in member
declaration
typedef int C::M3() const;
^

You can't typedef M3 to type 'member function', only
'pointer to member function'.

Quite a lot of the differences between free function types,
free function pointers and member function pointers are caused
by the need to be backwards compatible with C. It didn't have
member functions.

Regards,
Michiel Salters
 
T

tom_usenet

hi,
after reading some articles and faq,
i want to clarify myself what's correct(conform to standard) and
what's not?
or what should be correct but it isn't simply because compilers don't
support.
(first i compiled them with g++3.x. ERR means compiler will bark,
otherwise it does accept it. Then the Comeau C/C++ 4.3.3 comes)



//Q1===================================================//
--g++
typedef const int G(); //cv-qualified to int
typedef int F(); //function type

typedef const F H; //ERR, qualifier applied to function type means
nothing
Right.

typedef F const H; //what's it really? i don't know, but compiled with
g++

T const and const T are equivalent. Some people prefer to put the
const after since declarations are read right to left. e.g.

int const* const i; //const pointer to const int.
--Comeau
"ComeauTest.c", line 1: warning: type qualifier on return type is
meaningless
typedef const int G();
//well, different to what i think. what does std says?

Whereas const qualifiers on parameters are ignored in the function
type, const qualifiers on the return type are part of the function
type, so Comeau's (or EDG's) warning is at best misleading and at
worst plain wrong. You can detect the cv-qualification on the return
type easily enough, so it is hardly "meaningless".
"ComeauTest.c", line 3: warning: type qualifiers on function types are
ignored
typedef const F H;
^

Actually, if you form a const qualified function type as in your
example, the code is ill-formed. Comeau is conforming since it does
emit a diagnostic.
In strict mode, with -tused, Compile succeeded

It's not quite as strict as I'd expect, since you might expect those
warnings to be errors, but it is still conforming.
//Q2====================================================//
--g++
typedef int (*F2)(); //ok, function pointer "int (*)()"

the following two will be compiled by g++,
but i think they are trivial(or, they shouldn't be compiled?)
typedef const F2 H2; //qualifier applied to function pointer?
typedef F2 const H3; //like the above

They're fine - the const applies to the pointer, not the function.
//Q3=======================================================//
--g++
class C;
typedef int (C::*I)(); //a type of "int (C::*)()"
typedef int (C::*J)() const; //const member func, a type of "int
(C::*)() const"

typedef int (C::K)(); //ERR, typedef names can't be class qualified
well, seems reasonable to be ERR, but why?

You can't declare a qualified identifier. e.g. the example above

namespace N{}
typedef int N::T;

A qualified ID can only refer to something that has already been
declared. So you can do:

typedef int K();

class C
{
K foo; //int C::foo()
};

but you can't typedef a member function from outside the class
definition AFAIK, without using some template trickery (to remove the
pointer part of a member function pointer).
//Q4==================================================//
--g++
compiled ok, but should they be compiled ok?
class C;
typedef int Q();
typedef Q const C::* R1; //cv-qualified ptr?

(Removing the ill-formed const) that's equivalent to:
typedef int (C::*R1)();
typedef Q C::* const R2; //like the above

That's different, that's a const pointer. e.g.

R2 p = &C::somefunc;
p = 0; //not allowed - it's const
//--Comeau
"ComeauTest.c", line 3: warning: type qualifiers on function types are
ignored
typedef Q const C::* R1;

Again, the code is ill-formed because of the const qualified function
type.
//Q5======================================================//
--g++
typedef int M() const; //ERR, invalid qualifier for non-member func
type
why?

You can't cv qualify functions. The const in a member function
declaration is not cv qualification of the function type, but
something else (it's more like cv-qualification of a reference
parameter type - the cv-qualification of the hidden "this" parameter).

doesn't it implicitly expresses "int (someclass::*M)() const" and
let us do
the following:

class A
{
M mf;
};

--Comeau
In strict mode, with -tused, Compile succeeded

Again, it's ill-formed because of the const.

//Q6=====================================================//
--g++
class C
{
typedef int C::M3() const;

The above one is an error, the one below is fine.
typedef int M2() const; //ERR
in a class can't we get things done like above?

The second one is fine - it is a typedef for a parameterless const
member function of C returning int.
};

--Comeau
"ComeauTest.c", line 3: error: qualified name is not allowed in member
declaration
typedef int C::M3() const;
^
//well, different to what i think. what does std says?

Comeau is right.

Tin
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,744
Messages
2,569,482
Members
44,901
Latest member
Noble71S45

Latest Threads

Top