Opened 11 years ago
Closed 11 years ago
#6237 closed Bugs (invalid)
unordered_set behaves differently from 1.46 to 1.48
| Reported by: | Owned by: | Daniel James | |
|---|---|---|---|
| Milestone: | To Be Determined | Component: | unordered |
| Version: | Boost 1.48.0 | Severity: | Regression |
| Keywords: | Cc: |
Description
The following code runs OK on 1.46 but fails on 1.48. The correct output is "1".
// gcc -Iboost -lstdc++ test1.cpp
#include <iostream>
#include <boost/smart_ptr.hpp>
#include <boost/unordered_set.hpp>
namespace ns {
typedef boost::shared_ptr<class c> cptr;
typedef boost::unordered_set<cptr> cset;
class c
{
public:
c() { }
};
bool operator==(const cptr &c1, const cptr &c2) { return true; }
}
int main(int argc, char **argv)
{
ns::cptr bb1(new ns::c());
ns::cptr bb2(new ns::c());
ns::cset cs;
cs.insert(boost::dynamic_pointer_cast<ns::c>(bb1));
cs.insert(boost::dynamic_pointer_cast<ns::c>(bb1));
cs.insert(boost::dynamic_pointer_cast<ns::c>(bb2));
cs.insert(boost::dynamic_pointer_cast<ns::c>(bb2));
std::cout << "This should be 1: " << cs.size() << std::endl;
}
I'm using Xcode 4.2 / gcc on 10.6.8.
i686-apple-darwin10-llvm-gcc-4.2 (GCC) 4.2.1 (Based on Apple Inc. build 5658) (LLVM build 2336.1.00)
Change History (3)
comment:1 by , 11 years ago
comment:2 by , 11 years ago
Thanks for the explanation. This seems like a dangerous and non-obvious pitfall.
For reference, the documentation I missed is here:
http://www.boost.org/doc/libs/1_48_0/doc/html/unordered/hash_equality.html
This bug can be closed now.
comment:3 by , 11 years ago
| Resolution: | → invalid |
|---|---|
| Status: | new → closed |
Note:
See TracTickets
for help on using tickets.

No, it's valid, you're using a custom
operator==so for it to work you need to use a custom hash function. For this case,:bool operator==(const cptr &c1, const cptr &c2) { return true; } // Since cptr is always equal just hash to the same value. std::size_t hash_value(const cptr& c1) { return 1; }The hash function for your real code depends on what your equality operator does. This only worked before because there was a bug for hashing shared_ptr so they all went into the same bucket. This worked but was very inefficient.