Fix several range constructor bugs: (a) btree_multiset's range constructor did not compile (b) btree_map's range constructor ignored the inputs! These bugs were masked by the test, which due to an oversight skipped the use of range constructors as part of the {base,unique,multi}_checker testing types. Verified that the corrected test fails without the fix, added an additional sanity check (which made the problem stand out independent of the problems discovered in btree_test.h)
parent
5633058db4
commit
c790956d18
|
@ -261,8 +261,7 @@ class btree_map_container : public btree_unique_container<Tree> {
|
||||||
btree_map_container(InputIterator b, InputIterator e,
|
btree_map_container(InputIterator b, InputIterator e,
|
||||||
const key_compare &comp = key_compare(),
|
const key_compare &comp = key_compare(),
|
||||||
const allocator_type &alloc = allocator_type())
|
const allocator_type &alloc = allocator_type())
|
||||||
: super_type(comp, alloc) {
|
: super_type(b, e, comp, alloc) {
|
||||||
insert(b, e);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Insertion routines.
|
// Insertion routines.
|
||||||
|
@ -303,7 +302,7 @@ class btree_multi_container : public btree_container<Tree> {
|
||||||
btree_multi_container(InputIterator b, InputIterator e,
|
btree_multi_container(InputIterator b, InputIterator e,
|
||||||
const key_compare &comp = key_compare(),
|
const key_compare &comp = key_compare(),
|
||||||
const allocator_type &alloc = allocator_type())
|
const allocator_type &alloc = allocator_type())
|
||||||
: super_type(b, e, comp, alloc) {
|
: super_type(comp, alloc) {
|
||||||
insert(b, e);
|
insert(b, e);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -33,7 +33,7 @@
|
||||||
|
|
||||||
namespace btree {
|
namespace btree {
|
||||||
|
|
||||||
// The btree_map class is needed mainly for it's constructors.
|
// The btree_map class is needed mainly for its constructors.
|
||||||
template <typename Key, typename Value,
|
template <typename Key, typename Value,
|
||||||
typename Compare = std::less<Key>,
|
typename Compare = std::less<Key>,
|
||||||
typename Alloc = std::allocator<std::pair<const Key, Value> >,
|
typename Alloc = std::allocator<std::pair<const Key, Value> >,
|
||||||
|
@ -68,7 +68,7 @@ class btree_map : public btree_map_container<
|
||||||
btree_map(InputIterator b, InputIterator e,
|
btree_map(InputIterator b, InputIterator e,
|
||||||
const key_compare &comp = key_compare(),
|
const key_compare &comp = key_compare(),
|
||||||
const allocator_type &alloc = allocator_type())
|
const allocator_type &alloc = allocator_type())
|
||||||
: super_type(comp, alloc) {
|
: super_type(b, e, comp, alloc) {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -78,7 +78,7 @@ inline void swap(btree_map<K, V, C, A, N> &x,
|
||||||
x.swap(y);
|
x.swap(y);
|
||||||
}
|
}
|
||||||
|
|
||||||
// The btree_multimap class is needed mainly for it's constructors.
|
// The btree_multimap class is needed mainly for its constructors.
|
||||||
template <typename Key, typename Value,
|
template <typename Key, typename Value,
|
||||||
typename Compare = std::less<Key>,
|
typename Compare = std::less<Key>,
|
||||||
typename Alloc = std::allocator<std::pair<const Key, Value> >,
|
typename Alloc = std::allocator<std::pair<const Key, Value> >,
|
||||||
|
|
|
@ -29,7 +29,7 @@
|
||||||
|
|
||||||
namespace btree {
|
namespace btree {
|
||||||
|
|
||||||
// The btree_set class is needed mainly for it's constructors.
|
// The btree_set class is needed mainly for its constructors.
|
||||||
template <typename Key,
|
template <typename Key,
|
||||||
typename Compare = std::less<Key>,
|
typename Compare = std::less<Key>,
|
||||||
typename Alloc = std::allocator<Key>,
|
typename Alloc = std::allocator<Key>,
|
||||||
|
@ -72,7 +72,7 @@ inline void swap(btree_set<K, C, A, N> &x, btree_set<K, C, A, N> &y) {
|
||||||
x.swap(y);
|
x.swap(y);
|
||||||
}
|
}
|
||||||
|
|
||||||
// The btree_multiset class is needed mainly for it's constructors.
|
// The btree_multiset class is needed mainly for its constructors.
|
||||||
template <typename Key,
|
template <typename Key,
|
||||||
typename Compare = std::less<Key>,
|
typename Compare = std::less<Key>,
|
||||||
typename Alloc = std::allocator<Key>,
|
typename Alloc = std::allocator<Key>,
|
||||||
|
|
|
@ -244,5 +244,24 @@ TEST(Btree, Comparison) {
|
||||||
EXPECT_TRUE(my_map != my_map_copy);
|
EXPECT_TRUE(my_map != my_map_copy);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST(Btree, RangeCtorSanity) {
|
||||||
|
typedef btree_set<int, less<int>, allocator<int>, 256> test_set;
|
||||||
|
typedef btree_map<int, int, less<int>, allocator<int>, 256> test_map;
|
||||||
|
typedef btree_multiset<int, less<int>, allocator<int>, 256> test_mset;
|
||||||
|
typedef btree_multimap<int, int, less<int>, allocator<int>, 256> test_mmap;
|
||||||
|
vector<int> ivec;
|
||||||
|
ivec.push_back(1);
|
||||||
|
map<int, int> imap;
|
||||||
|
imap.insert(make_pair(1, 2));
|
||||||
|
test_mset tmset(ivec.begin(), ivec.end());
|
||||||
|
test_mmap tmmap(imap.begin(), imap.end());
|
||||||
|
test_set tset(ivec.begin(), ivec.end());
|
||||||
|
test_map tmap(imap.begin(), imap.end());
|
||||||
|
EXPECT_EQ(1, tmset.size());
|
||||||
|
EXPECT_EQ(1, tmmap.size());
|
||||||
|
EXPECT_EQ(1, tset.size());
|
||||||
|
EXPECT_EQ(1, tmap.size());
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
} // namespace btree
|
} // namespace btree
|
||||||
|
|
16
btree_test.h
16
btree_test.h
|
@ -147,6 +147,13 @@ class base_checker {
|
||||||
const_tree_(tree_),
|
const_tree_(tree_),
|
||||||
checker_(x.checker_) {
|
checker_(x.checker_) {
|
||||||
}
|
}
|
||||||
|
// Range constructor.
|
||||||
|
template <typename InputIterator>
|
||||||
|
base_checker(InputIterator b, InputIterator e)
|
||||||
|
: tree_(b, e),
|
||||||
|
const_tree_(tree_),
|
||||||
|
checker_(b, e) {
|
||||||
|
}
|
||||||
|
|
||||||
// Iterator routines.
|
// Iterator routines.
|
||||||
iterator begin() { return tree_.begin(); }
|
iterator begin() { return tree_.begin(); }
|
||||||
|
@ -398,8 +405,8 @@ class unique_checker : public base_checker<TreeType, CheckerType> {
|
||||||
}
|
}
|
||||||
// Range constructor.
|
// Range constructor.
|
||||||
template <class InputIterator>
|
template <class InputIterator>
|
||||||
unique_checker(InputIterator b, InputIterator e) {
|
unique_checker(InputIterator b, InputIterator e)
|
||||||
insert(b, e);
|
: super_type(b, e) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Insertion routines.
|
// Insertion routines.
|
||||||
|
@ -455,8 +462,8 @@ class multi_checker : public base_checker<TreeType, CheckerType> {
|
||||||
}
|
}
|
||||||
// Range constructor.
|
// Range constructor.
|
||||||
template <class InputIterator>
|
template <class InputIterator>
|
||||||
multi_checker(InputIterator b, InputIterator e) {
|
multi_checker(InputIterator b, InputIterator e)
|
||||||
insert(b, e);
|
: super_type(b, e) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Insertion routines.
|
// Insertion routines.
|
||||||
|
@ -587,6 +594,7 @@ void DoTest(const char *name, T *b, const std::vector<V> &values) {
|
||||||
mutable_b.insert(values[i]);
|
mutable_b.insert(values[i]);
|
||||||
mutable_b.value_check(values[i]);
|
mutable_b.value_check(values[i]);
|
||||||
}
|
}
|
||||||
|
assert(mutable_b.size() == values.size());
|
||||||
|
|
||||||
const_b.verify();
|
const_b.verify();
|
||||||
printf(" %s fullness=%0.2f overhead=%0.2f bytes-per-value=%0.2f\n",
|
printf(" %s fullness=%0.2f overhead=%0.2f bytes-per-value=%0.2f\n",
|
||||||
|
|
Loading…
Reference in New Issue