#2908 closed Bugs (fixed)
unordered_map has no destructor!
Reported by: | anonymous | Owned by: | Daniel James |
---|---|---|---|
Milestone: | Boost 1.39.0 | Component: | unordered |
Version: | Boost 1.37.0 | Severity: | Problem |
Keywords: | unordered_map, destructor | Cc: |
Description
I noticed that the unordered_map has no destructor as one would assume. There should be a destructor that calls clear() so that the content of the map is deleted. (cf. RAII - http://en.wikipedia.org/wiki/Resource_Acquisition_Is_Initialization)
I ran into a serious memory leak because of that, when using an unordered_map locally and assuming that it clears its content when being destroyed.
Change History (8)
comment:1 by , 14 years ago
Resolution: | → invalid |
---|---|
Status: | new → closed |
comment:2 by , 14 years ago
But somehow the unordered_map was only cleared if and only if I called clear() manually. I can post you some details if you like.
comment:3 by , 14 years ago
If you send me an example, I'll have a look at it. Let me know which compiler you're using and on which platform.
comment:4 by , 13 years ago
Version: | Boost 1.38.0 → Boost 1.37.0 |
---|
Here is the example (I tried to skip the unnecessary stuff):
definitions:
typedef boost::tuple<TPoint, TPoint, TPoint> TEdgeIdentifier; typedef std::pair<PTempPlzEdge, unsigned> TCountedEdge;
typedef boost::unordered_map<TEdgeIdentifier, TCountedEdge, TEdgeIdentifierHash, TEdgeIdentifierEqual> TEdgeCountMap;
method:
TEdgeCountMap EdgeCountDifferentMap( 1.5 * List.size() ); for( "it in List" ){
TEdgeCountMap::iterator found = EdgeCountDifferentMap.find( (*it)->GetEdgeIdentifier() );
if( found != EdgeCountDifferentMap.end() ){
if( "some condition" ){
found->second.second ++;
}
}else{
EdgeCountDifferentMap.insert( std::make_pair( (*it)->GetEdgeIdentifier(), std::make_pair( *it , 1 ) ) );
}
}
for( "it in List" ){
TEdgeCountMap::iterator found = EdgeCountDifferentMap.find( (*it)->GetEdgeIdentifier() );
if( found != EdgeCountDifferentMap.end() && found->second.second > 1 ){
continue;
}
"do something with *it"
}
EdgeCountDifferentMap.clear(); if this is uncommented, I have a huge memory leak although this is the end of the method and EdgeCountDifferentMap should be destroyed
Additionally I noticed (using AQtime 6) that the memory that is allocated within the constructor call "TEdgeCountMap EdgeCountDifferentMap( 1.5 * List.size() );" is not freed too.
I am in the unfortunate situation that I have to use Borland C++ Builder 4. I use boost version 1.37.
comment:5 by , 13 years ago
Resolution: | invalid |
---|---|
Status: | closed → reopened |
comment:6 by , 13 years ago
comment:7 by , 13 years ago
Resolution: | → fixed |
---|---|
Status: | reopened → closed |
Well, guess what? That worked! Strange, as I can comprehend your previous reasoning totaly. Seems like the old Borland C++-Compiler has a serious issue there. :(
comment:8 by , 13 years ago
(In [53465]) Merge latest changes for unordered. Improved compatability and a few tweaks.
Merged revisions 53127,53253,53256,53311,53314,53316-53318 via svnmerge from https://svn.boost.org/svn/boost/trunk
........
r53127 | danieljames | 2009-05-20 07:43:38 +0100 (Wed, 20 May 2009) | 1 line
Better configuration for boost.unordered.
........
r53253 | danieljames | 2009-05-25 20:14:07 +0100 (Mon, 25 May 2009) | 3 lines
Add explicit destructors to the unordered containers. Refs #2908.
Isn't really needed but it doesn't hurt.
........
r53256 | danieljames | 2009-05-25 20:45:23 +0100 (Mon, 25 May 2009) | 1 line
Unordered change log for explicit destructors.
........
r53311 | danieljames | 2009-05-27 18:42:01 +0100 (Wed, 27 May 2009) | 1 line
Missing changelog entry.
........
r53314 | danieljames | 2009-05-27 18:44:09 +0100 (Wed, 27 May 2009) | 1 line
Use lightweight_test for unordered.
........
r53316 | danieljames | 2009-05-27 19:19:32 +0100 (Wed, 27 May 2009) | 1 line
Some workarounds for old versions of Borland.
........
r53317 | danieljames | 2009-05-27 19:32:22 +0100 (Wed, 27 May 2009) | 1 line
Fix a change accidentally included in the last commit.
........
r53318 | danieljames | 2009-05-27 19:32:38 +0100 (Wed, 27 May 2009) | 1 line
Remove an unused function.
........
The memory management is taken care of by an internal implementation class called
hash_table_data_equivalent_keys
orhash_table_data_unique_keys
. You can see the destructor here:https://svn.boost.org/trac/boost/browser/trunk/boost/unordered/detail/hash_table_impl.hpp?rev=51995#L380
The destructor is called
BOOST_UNORDERED_TABLE_DATA
because I'm using macros to define the two different hash tables with a single implementation.unordered_map
andunordered_set
's implicit destructors both call the implementation classes' destructors, so there's no need to define a destructor for those classes.