map, pair and function pointer

M

Marco Segurini

Hi,

I am asking myself, why the compilation of line 21 and 22 fail using
Visual Studio 2002.

Begin program --------------------------
#include <map>

class TestMap
{
typedef void (TestMap::*ptrCmd)();
typedef std::pair<long,ptrCmd> LongPtrFnPair;

std::map<long,ptrCmd> m_map;

void Cmd1();
void Cmd2();
void Cmd3();

public:
TestMap();
};


TestMap::TestMap()
{
m_map.insert(LongPtrFnPair(1, Cmd1)); //line 21
m_map.insert(LongPtrFnPair(2, TestMap::Cmd2)); //line 22
m_map.insert(LongPtrFnPair(3, &TestMap::Cmd3)); //line 23
}

void TestMap::Cmd1() {}
void TestMap::Cmd2() {}
void TestMap::Cmd3() {}


int main()
{
TestMap TM;

return 0;
}
End program ---------------

Compiling...
MapPair.cpp
e:\Prove\C++ NET\MapPair\MapPair.cpp(21) : error C2665:
'std::pair::__ctor' : none of the 3 overloads can convert parameter 2
from type 'void (void)'
c:\Programmi\Microsoft Visual Studio
..NET\Vc7\include\utility(32): could be 'std::pair<_Ty1,_Ty2>::pair(const
_Ty1 &,const TestMap::ptrCmd & )'
with
[
_Ty1=long,
_Ty2=TestMap::ptrCmd
]
while trying to match the argument list '(int,
overloaded-function)'
e:\Prove\C++ NET\MapPair\MapPair.cpp(22) : error C2665:
'std::pair::__ctor' : none of the 3 overloads can convert parameter 2
from type 'void (void)'
c:\Programmi\Microsoft Visual Studio
..NET\Vc7\include\utility(32): could be 'std::pair<_Ty1,_Ty2>::pair(const
_Ty1 &,const TestMap::ptrCmd & )'
with
[
_Ty1=long,
_Ty2=TestMap::ptrCmd
]
while trying to match the argument list '(int,
overloaded-function)'

End build log -------------------


TIA.
Marco.
 
H

Hendrik Schober

Marco Segurini said:
Hi,

I am asking myself, why the compilation of line 21 and 22 fail using
Visual Studio 2002.
[...]

This is what Comeau says:

Comeau C/C++ 4.3.3 (Aug 6 2003 15:13:37) for ONLINE_EVALUATION_BETA1
Copyright 1988-2003 Comeau Computing. All rights reserved.
MODE:strict errors C++

"ComeauTest.c", line 21: error: nonstandard form for taking the address of a member
function
m_map.insert(LongPtrFnPair(1, Cmd1)); //line 21
^

"ComeauTest.c", line 22: error: nonstandard form for taking the address of a member
function
m_map.insert(LongPtrFnPair(2, TestMap::Cmd2)); //line 22
^

2 errors detected in the compilation of "ComeauTest.c".
[...]

TIA.
Marco.

Schobi

--
(e-mail address removed) is never read
I'm Schobi at suespammers dot org

"Sometimes compilers are so much more reasonable than people."
Scott Meyers
 
C

Carl Daniel [VC++ MVP]

Marco said:
Hi,

I am asking myself, why the compilation of line 21 and 22 fail using
Visual Studio 2002.

To elaborate on Schobi's post - they're required to fail according to the
C++ standard. Unlike ordinary pointers to functions, the only way to create
a pointer to member function is to apply the unary address-of operator (&)
to a qualified name that nominates a function member.

-cd
 
M

Marco Segurini

Carl said:
To elaborate on Schobi's post - they're required to fail according to the
C++ standard. Unlike ordinary pointers to functions, the only way to create
a pointer to member function is to apply the unary address-of operator (&)
to a qualified name that nominates a function member.

-cd

Thanks!

.... but Visual Studio 2003 builds this program with no errors or
warnings using /W4.

Bye.
Marco
 
T

tom_usenet

Thanks!

... but Visual Studio 2003 builds this program with no errors or
warnings using /W4.

You need to disable extensions to get an error (/Za). MSVC has a lot
of extensions to standard C++ that you should avoid using if you want
portable code, or even code that will work with future versions of
MSVC.

Relying on the compiler to tell you what is portable code is not a
good idea.

Tom
 
M

Marco Segurini

tom_usenet said:
You need to disable extensions to get an error (/Za). MSVC has a lot
of extensions to standard C++ that you should avoid using if you want
portable code, or even code that will work with future versions of
MSVC.

Relying on the compiler to tell you what is portable code is not a
good idea.

Tom

Thanks a lot for the reply.

The use of /Za in my solutions involves a large list of compiler errors
on MFC code (example: '__interface' keyword).


Bye.
Marco
 
H

Hendrik Schober

Marco Segurini said:
[...]
The use of /Za in my solutions involves a large list of compiler errors
on MFC code (example: '__interface' keyword).

Yes. Unfortunately, /Za is rather useless.
Bye.
Marco

Schobi

--
(e-mail address removed) is never read
I'm Schobi at suespammers dot org

"Sometimes compilers are so much more reasonable than people."
Scott Meyers
 
T

tom_usenet

Thanks a lot for the reply.

The use of /Za in my solutions involves a large list of compiler errors
on MFC code (example: '__interface' keyword).

Yup, you can't use /Za is MFC or even most Win32 code. Don't rely on
the compiler to tell you what is standard, rely on your knowledge of
what is standard (read a good book on the subject, check constructs
before using them, etc.). Unless of course portability is not an
issue, but usually the ability to at least move to a different
compiler version is important, even if you stick to Windows. And if
you don't know how something is supposed to work, you can end up
relying on undefined behaviour that might change even after a
recompile.

In the worst case code will compile both in the old version and the
new version of the compiler, but have subtly different semantics in
each case. The introduction of two phase name lookup in the future
could cause such problems, for example.

Tom
 

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

Top