By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
445,898 Members | 2,006 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 445,898 IT Pros & Developers. It's quick & easy.

Undefined end() in extended map template

P: n/a
Hi all,

I have this template which does not compile with "Compaq C++ V6.5-004
for OpenVMS Alpha V7.3-1" and Comeau C/C++ 4.3.3. This looks like
there must really be error in the code:

#include <map>

template <class Key, class T, class Compare = std::less<Key>,
class Allocator = std::allocator<std::pair<const Key, T> > >
class map_of_objects : public std::map<Key, T, Compare, Allocator>
{
typedef typename std::map<Key, T, Compare, Allocator> parent_tpl;

public:
typedef Key key_type;
typedef typename Allocator::size_type size_type;
typedef typename parent_tpl::iterator iterator;

size_type erase(const key_type& x)
{
iterator i = *find(x);
if (i != end())
{
delete *i;
}
parent_tpl::erase(x);
}
};

It compiles fine in Borland C++ 5.5 and Compaq C++ V6.2-048 for
OpenVMS Alpha V7.3. I do not understand why end() is undefined and
find() is defined. There must be something I really miss. This problem
can be solved by using "this->end()" or "using parent_tpl end;".
However, I still do not understand what I am doing wrong.

Ondrej
Jul 22 '05 #1
Share this Question
Share on Google+
1 Reply


P: n/a
Ondrej Brablc wrote in
news:b8**************************@posting.google.c om:
Hi all,

I have this template which does not compile with "Compaq C++ V6.5-004
for OpenVMS Alpha V7.3-1" and Comeau C/C++ 4.3.3. This looks like
there must really be error in the code:

#include <map>

template <class Key, class T, class Compare = std::less<Key>,
class Allocator = std::allocator<std::pair<const Key, T> > >
class map_of_objects : public std::map<Key, T, Compare, Allocator>
{
typedef typename std::map<Key, T, Compare, Allocator> parent_tpl;

public:
typedef Key key_type;
typedef typename Allocator::size_type size_type;
typedef typename parent_tpl::iterator iterator;

size_type erase(const key_type& x)
{
iterator i = *find(x);
This should be:

iterator i = this->find(x);

if (i != end())
if (i != this->end())
or
if (i != parent_tpl::end())
{
delete *i;
}
parent_tpl::erase(x);
}
};

It compiles fine in Borland C++ 5.5 and Compaq C++ V6.2-048 for
OpenVMS Alpha V7.3. I do not understand why end() is undefined and
find() is defined. There must be something I really miss. This problem
can be solved by using "this->end()" or "using parent_tpl end;".
However, I still do not understand what I am doing wrong.


You're not telling the compiler that end() is a dependant name.
The compilers that compile this are not *fully* conforming with the
C++ Standard.

A "dependant name" is a name (identifier) that is dependant on 1 or
more template paramiters. In this case since std::map<Key, T, Compare,
Allocator> (i.e. parent_tpl) depends on template paramiters, then its
members are dependant on template paramiters.

The conforming compilers implement 2-phase name lookup. When they first
encounter your template declaration's they check them, including looking
up all the identifiers that they encounter. The reason an error wasn't
given for find( x ) is its paramiter 'x', since 'x' is of dependant type
then clearly the find in 'find( x )' is a dependant name, so the compiler
doesn't try to look it up.

Consider:

template < typename T >
stuct X
{
void dependant_name();
};

template < typename T >
stuct X< T * > // partial specialization
{
void dependant_name();
};

template < typename T >
struct Y : X< T >
{
void non_pointers()
{
dependant_name();
}
};

Also the following is included later (at global scope):

void dependant_name();

Then:

int main()
{
Y< int * > y;

y.non_pointers();
}

Note that above, in main(), the call y.non_pointers() is an error,
but the non-conforming compilers compile it and call the global
dependant_name(), which has *nothing* to do with the templates X<>
and Y<>.

The conforming compilers should complain that the identifier
dependant_name in Y<>::non_pointers() hasn't been declared.

HTH (and wasn't to long winded).

Rob.
--
http://www.victim-prime.dsl.pipex.com/
Jul 22 '05 #2

This discussion thread is closed

Replies have been disabled for this discussion.