2010-11-19 04:47:19 +00:00
|
|
|
//===---- ADT/IntervalMapTest.cpp - IntervalMap unit tests ------*- C++ -*-===//
|
|
|
|
//
|
|
|
|
// The LLVM Compiler Infrastructure
|
|
|
|
//
|
|
|
|
// This file is distributed under the University of Illinois Open Source
|
|
|
|
// License. See LICENSE.TXT for details.
|
|
|
|
//
|
|
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
|
|
|
|
#include "llvm/ADT/IntervalMap.h"
|
|
|
|
#include "gtest/gtest.h"
|
|
|
|
|
|
|
|
using namespace llvm;
|
|
|
|
|
|
|
|
namespace {
|
|
|
|
|
2010-12-03 19:02:00 +00:00
|
|
|
typedef IntervalMap<unsigned, unsigned, 4> UUMap;
|
2010-11-19 04:47:19 +00:00
|
|
|
|
|
|
|
// Empty map tests
|
|
|
|
TEST(IntervalMapTest, EmptyMap) {
|
|
|
|
UUMap::Allocator allocator;
|
|
|
|
UUMap map(allocator);
|
|
|
|
EXPECT_TRUE(map.empty());
|
|
|
|
|
|
|
|
// Lookup on empty map.
|
|
|
|
EXPECT_EQ(0u, map.lookup(0));
|
|
|
|
EXPECT_EQ(7u, map.lookup(0, 7));
|
|
|
|
EXPECT_EQ(0u, map.lookup(~0u-1));
|
|
|
|
EXPECT_EQ(7u, map.lookup(~0u-1, 7));
|
|
|
|
|
|
|
|
// Iterators.
|
|
|
|
EXPECT_TRUE(map.begin() == map.begin());
|
|
|
|
EXPECT_TRUE(map.begin() == map.end());
|
|
|
|
EXPECT_TRUE(map.end() == map.end());
|
|
|
|
EXPECT_FALSE(map.begin() != map.begin());
|
|
|
|
EXPECT_FALSE(map.begin() != map.end());
|
|
|
|
EXPECT_FALSE(map.end() != map.end());
|
|
|
|
EXPECT_FALSE(map.begin().valid());
|
|
|
|
EXPECT_FALSE(map.end().valid());
|
|
|
|
UUMap::iterator I = map.begin();
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
EXPECT_TRUE(I == map.end());
|
2010-11-28 07:21:48 +00:00
|
|
|
|
|
|
|
// Default constructor and cross-constness compares.
|
|
|
|
UUMap::const_iterator CI;
|
|
|
|
CI = map.begin();
|
|
|
|
EXPECT_TRUE(CI == I);
|
|
|
|
UUMap::iterator I2;
|
|
|
|
I2 = map.end();
|
|
|
|
EXPECT_TRUE(I2 == CI);
|
2010-11-19 04:47:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Single entry map tests
|
|
|
|
TEST(IntervalMapTest, SingleEntryMap) {
|
|
|
|
UUMap::Allocator allocator;
|
|
|
|
UUMap map(allocator);
|
|
|
|
map.insert(100, 150, 1);
|
|
|
|
EXPECT_FALSE(map.empty());
|
|
|
|
|
|
|
|
// Lookup around interval.
|
|
|
|
EXPECT_EQ(0u, map.lookup(0));
|
|
|
|
EXPECT_EQ(0u, map.lookup(99));
|
|
|
|
EXPECT_EQ(1u, map.lookup(100));
|
|
|
|
EXPECT_EQ(1u, map.lookup(101));
|
|
|
|
EXPECT_EQ(1u, map.lookup(125));
|
|
|
|
EXPECT_EQ(1u, map.lookup(149));
|
|
|
|
EXPECT_EQ(1u, map.lookup(150));
|
|
|
|
EXPECT_EQ(0u, map.lookup(151));
|
|
|
|
EXPECT_EQ(0u, map.lookup(200));
|
|
|
|
EXPECT_EQ(0u, map.lookup(~0u-1));
|
|
|
|
|
|
|
|
// Iterators.
|
|
|
|
EXPECT_TRUE(map.begin() == map.begin());
|
|
|
|
EXPECT_FALSE(map.begin() == map.end());
|
|
|
|
EXPECT_TRUE(map.end() == map.end());
|
|
|
|
EXPECT_TRUE(map.begin().valid());
|
|
|
|
EXPECT_FALSE(map.end().valid());
|
|
|
|
|
|
|
|
// Iter deref.
|
|
|
|
UUMap::iterator I = map.begin();
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(100u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
EXPECT_EQ(1u, I.value());
|
|
|
|
|
|
|
|
// Preincrement.
|
|
|
|
++I;
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
EXPECT_FALSE(I == map.begin());
|
|
|
|
EXPECT_TRUE(I == map.end());
|
|
|
|
|
|
|
|
// PreDecrement.
|
|
|
|
--I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(100u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
EXPECT_EQ(1u, I.value());
|
|
|
|
EXPECT_TRUE(I == map.begin());
|
|
|
|
EXPECT_FALSE(I == map.end());
|
2010-11-27 22:56:53 +00:00
|
|
|
|
2010-12-03 19:02:00 +00:00
|
|
|
// Change the value.
|
|
|
|
I.setValue(2);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(100u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
EXPECT_EQ(2u, I.value());
|
|
|
|
|
|
|
|
// Grow the bounds.
|
|
|
|
I.setStart(0);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(0u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
EXPECT_EQ(2u, I.value());
|
|
|
|
|
|
|
|
I.setStop(200);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(0u, I.start());
|
|
|
|
EXPECT_EQ(200u, I.stop());
|
|
|
|
EXPECT_EQ(2u, I.value());
|
|
|
|
|
|
|
|
// Shrink the bounds.
|
|
|
|
I.setStart(150);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(150u, I.start());
|
|
|
|
EXPECT_EQ(200u, I.stop());
|
|
|
|
EXPECT_EQ(2u, I.value());
|
|
|
|
|
|
|
|
I.setStop(160);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(150u, I.start());
|
|
|
|
EXPECT_EQ(160u, I.stop());
|
|
|
|
EXPECT_EQ(2u, I.value());
|
|
|
|
|
|
|
|
// Erase last elem.
|
2010-11-27 22:56:53 +00:00
|
|
|
I.erase();
|
|
|
|
EXPECT_TRUE(map.empty());
|
|
|
|
EXPECT_EQ(0, std::distance(map.begin(), map.end()));
|
2010-11-19 04:47:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Flat coalescing tests.
|
|
|
|
TEST(IntervalMapTest, RootCoalescing) {
|
|
|
|
UUMap::Allocator allocator;
|
|
|
|
UUMap map(allocator);
|
|
|
|
map.insert(100, 150, 1);
|
|
|
|
|
|
|
|
// Coalesce from the left.
|
|
|
|
map.insert(90, 99, 1);
|
|
|
|
EXPECT_EQ(1, std::distance(map.begin(), map.end()));
|
|
|
|
EXPECT_EQ(90u, map.start());
|
|
|
|
EXPECT_EQ(150u, map.stop());
|
|
|
|
|
|
|
|
// Coalesce from the right.
|
2010-11-28 22:17:11 +00:00
|
|
|
map.insert(151, 200, 1);
|
2010-11-19 04:47:19 +00:00
|
|
|
EXPECT_EQ(1, std::distance(map.begin(), map.end()));
|
2010-11-28 22:17:11 +00:00
|
|
|
EXPECT_EQ(90u, map.start());
|
2010-11-19 04:47:19 +00:00
|
|
|
EXPECT_EQ(200u, map.stop());
|
|
|
|
|
|
|
|
// Non-coalesce from the left.
|
2010-11-28 22:17:11 +00:00
|
|
|
map.insert(60, 89, 2);
|
2010-11-19 04:47:19 +00:00
|
|
|
EXPECT_EQ(2, std::distance(map.begin(), map.end()));
|
|
|
|
EXPECT_EQ(60u, map.start());
|
|
|
|
EXPECT_EQ(200u, map.stop());
|
2010-11-28 22:17:11 +00:00
|
|
|
EXPECT_EQ(2u, map.lookup(89));
|
|
|
|
EXPECT_EQ(1u, map.lookup(90));
|
2010-11-19 04:47:19 +00:00
|
|
|
|
|
|
|
UUMap::iterator I = map.begin();
|
|
|
|
EXPECT_EQ(60u, I.start());
|
2010-11-28 22:17:11 +00:00
|
|
|
EXPECT_EQ(89u, I.stop());
|
2010-11-19 04:47:19 +00:00
|
|
|
EXPECT_EQ(2u, I.value());
|
|
|
|
++I;
|
2010-11-28 22:17:11 +00:00
|
|
|
EXPECT_EQ(90u, I.start());
|
2010-11-19 04:47:19 +00:00
|
|
|
EXPECT_EQ(200u, I.stop());
|
|
|
|
EXPECT_EQ(1u, I.value());
|
|
|
|
++I;
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
|
|
|
|
// Non-coalesce from the right.
|
|
|
|
map.insert(201, 210, 2);
|
|
|
|
EXPECT_EQ(3, std::distance(map.begin(), map.end()));
|
|
|
|
EXPECT_EQ(60u, map.start());
|
|
|
|
EXPECT_EQ(210u, map.stop());
|
|
|
|
EXPECT_EQ(2u, map.lookup(201));
|
|
|
|
EXPECT_EQ(1u, map.lookup(200));
|
2010-11-27 22:56:53 +00:00
|
|
|
|
|
|
|
// Erase from the left.
|
|
|
|
map.begin().erase();
|
|
|
|
EXPECT_EQ(2, std::distance(map.begin(), map.end()));
|
2010-11-28 22:17:11 +00:00
|
|
|
EXPECT_EQ(90u, map.start());
|
2010-11-27 22:56:53 +00:00
|
|
|
EXPECT_EQ(210u, map.stop());
|
|
|
|
|
|
|
|
// Erase from the right.
|
|
|
|
(--map.end()).erase();
|
|
|
|
EXPECT_EQ(1, std::distance(map.begin(), map.end()));
|
2010-11-28 22:17:11 +00:00
|
|
|
EXPECT_EQ(90u, map.start());
|
2010-11-27 22:56:53 +00:00
|
|
|
EXPECT_EQ(200u, map.stop());
|
2010-12-03 19:02:00 +00:00
|
|
|
|
|
|
|
// Add non-coalescing, then trigger coalescing with setValue.
|
|
|
|
map.insert(80, 89, 2);
|
|
|
|
map.insert(201, 210, 2);
|
|
|
|
EXPECT_EQ(3, std::distance(map.begin(), map.end()));
|
|
|
|
(++map.begin()).setValue(2);
|
|
|
|
EXPECT_EQ(1, std::distance(map.begin(), map.end()));
|
|
|
|
I = map.begin();
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(80u, I.start());
|
|
|
|
EXPECT_EQ(210u, I.stop());
|
|
|
|
EXPECT_EQ(2u, I.value());
|
2010-11-19 04:47:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Flat multi-coalescing tests.
|
|
|
|
TEST(IntervalMapTest, RootMultiCoalescing) {
|
|
|
|
UUMap::Allocator allocator;
|
|
|
|
UUMap map(allocator);
|
|
|
|
map.insert(140, 150, 1);
|
|
|
|
map.insert(160, 170, 1);
|
|
|
|
map.insert(100, 110, 1);
|
|
|
|
map.insert(120, 130, 1);
|
|
|
|
EXPECT_EQ(4, std::distance(map.begin(), map.end()));
|
|
|
|
EXPECT_EQ(100u, map.start());
|
|
|
|
EXPECT_EQ(170u, map.stop());
|
|
|
|
|
|
|
|
// Verify inserts.
|
|
|
|
UUMap::iterator I = map.begin();
|
|
|
|
EXPECT_EQ(100u, I.start());
|
|
|
|
EXPECT_EQ(110u, I.stop());
|
|
|
|
++I;
|
|
|
|
EXPECT_EQ(120u, I.start());
|
|
|
|
EXPECT_EQ(130u, I.stop());
|
|
|
|
++I;
|
|
|
|
EXPECT_EQ(140u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
++I;
|
|
|
|
EXPECT_EQ(160u, I.start());
|
|
|
|
EXPECT_EQ(170u, I.stop());
|
|
|
|
++I;
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
|
2010-11-28 07:00:46 +00:00
|
|
|
// Test advanceTo on flat tree.
|
|
|
|
I = map.begin();
|
|
|
|
I.advanceTo(135);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(140u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
|
|
|
|
I.advanceTo(145);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(140u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
2010-11-19 04:47:19 +00:00
|
|
|
|
|
|
|
// Coalesce left with followers.
|
|
|
|
// [100;110] [120;130] [140;150] [160;170]
|
|
|
|
map.insert(111, 115, 1);
|
|
|
|
I = map.begin();
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(100u, I.start());
|
|
|
|
EXPECT_EQ(115u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(120u, I.start());
|
|
|
|
EXPECT_EQ(130u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(140u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(160u, I.start());
|
|
|
|
EXPECT_EQ(170u, I.stop());
|
|
|
|
++I;
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
|
|
|
|
// Coalesce right with followers.
|
|
|
|
// [100;115] [120;130] [140;150] [160;170]
|
|
|
|
map.insert(135, 139, 1);
|
|
|
|
I = map.begin();
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(100u, I.start());
|
|
|
|
EXPECT_EQ(115u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(120u, I.start());
|
|
|
|
EXPECT_EQ(130u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(135u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(160u, I.start());
|
|
|
|
EXPECT_EQ(170u, I.stop());
|
|
|
|
++I;
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
|
|
|
|
// Coalesce left and right with followers.
|
|
|
|
// [100;115] [120;130] [135;150] [160;170]
|
|
|
|
map.insert(131, 134, 1);
|
|
|
|
I = map.begin();
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(100u, I.start());
|
|
|
|
EXPECT_EQ(115u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(120u, I.start());
|
|
|
|
EXPECT_EQ(150u, I.stop());
|
|
|
|
++I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(160u, I.start());
|
|
|
|
EXPECT_EQ(170u, I.stop());
|
|
|
|
++I;
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
|
2010-11-19 23:28:57 +00:00
|
|
|
// Test clear() on non-branched map.
|
|
|
|
map.clear();
|
|
|
|
EXPECT_TRUE(map.empty());
|
|
|
|
EXPECT_TRUE(map.begin() == map.end());
|
2010-11-19 04:47:19 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Branched, non-coalescing tests.
|
|
|
|
TEST(IntervalMapTest, Branched) {
|
|
|
|
UUMap::Allocator allocator;
|
|
|
|
UUMap map(allocator);
|
|
|
|
|
|
|
|
// Insert enough intervals to force a branched tree.
|
|
|
|
// This creates 9 leaf nodes with 11 elements each, tree height = 1.
|
2010-11-27 22:56:53 +00:00
|
|
|
for (unsigned i = 1; i < 100; ++i) {
|
2010-11-19 04:47:19 +00:00
|
|
|
map.insert(10*i, 10*i+5, i);
|
2010-11-27 22:56:53 +00:00
|
|
|
EXPECT_EQ(10u, map.start());
|
|
|
|
EXPECT_EQ(10*i+5, map.stop());
|
|
|
|
}
|
2010-11-19 04:47:19 +00:00
|
|
|
|
|
|
|
// Tree limits.
|
|
|
|
EXPECT_FALSE(map.empty());
|
|
|
|
EXPECT_EQ(10u, map.start());
|
|
|
|
EXPECT_EQ(995u, map.stop());
|
|
|
|
|
|
|
|
// Tree lookup.
|
|
|
|
for (unsigned i = 1; i < 100; ++i) {
|
|
|
|
EXPECT_EQ(0u, map.lookup(10*i-1));
|
|
|
|
EXPECT_EQ(i, map.lookup(10*i));
|
|
|
|
EXPECT_EQ(i, map.lookup(10*i+5));
|
|
|
|
EXPECT_EQ(0u, map.lookup(10*i+6));
|
|
|
|
}
|
|
|
|
|
|
|
|
// Forward iteration.
|
|
|
|
UUMap::iterator I = map.begin();
|
|
|
|
for (unsigned i = 1; i < 100; ++i) {
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(10*i, I.start());
|
|
|
|
EXPECT_EQ(10*i+5, I.stop());
|
|
|
|
EXPECT_EQ(i, *I);
|
|
|
|
++I;
|
|
|
|
}
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
EXPECT_TRUE(I == map.end());
|
|
|
|
|
2010-11-19 23:28:53 +00:00
|
|
|
// Backwards iteration.
|
|
|
|
for (unsigned i = 99; i; --i) {
|
|
|
|
--I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(10*i, I.start());
|
|
|
|
EXPECT_EQ(10*i+5, I.stop());
|
|
|
|
EXPECT_EQ(i, *I);
|
|
|
|
}
|
|
|
|
EXPECT_TRUE(I == map.begin());
|
|
|
|
|
2010-11-28 07:00:46 +00:00
|
|
|
// Test advanceTo in same node.
|
|
|
|
I.advanceTo(20);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(20u, I.start());
|
|
|
|
EXPECT_EQ(25u, I.stop());
|
|
|
|
|
2010-12-03 19:02:00 +00:00
|
|
|
// Change value, no coalescing.
|
|
|
|
I.setValue(0);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(20u, I.start());
|
|
|
|
EXPECT_EQ(25u, I.stop());
|
|
|
|
EXPECT_EQ(0u, I.value());
|
|
|
|
|
|
|
|
// Close the gap right, no coalescing.
|
|
|
|
I.setStop(29);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(20u, I.start());
|
|
|
|
EXPECT_EQ(29u, I.stop());
|
|
|
|
EXPECT_EQ(0u, I.value());
|
|
|
|
|
|
|
|
// Change value, no coalescing.
|
|
|
|
I.setValue(2);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(20u, I.start());
|
|
|
|
EXPECT_EQ(29u, I.stop());
|
|
|
|
EXPECT_EQ(2u, I.value());
|
|
|
|
|
|
|
|
// Change value, now coalescing.
|
|
|
|
I.setValue(3);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(20u, I.start());
|
|
|
|
EXPECT_EQ(35u, I.stop());
|
|
|
|
EXPECT_EQ(3u, I.value());
|
|
|
|
|
|
|
|
// Close the gap, now coalescing.
|
|
|
|
I.setValue(4);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
I.setStop(39);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(20u, I.start());
|
|
|
|
EXPECT_EQ(45u, I.stop());
|
|
|
|
EXPECT_EQ(4u, I.value());
|
|
|
|
|
2010-11-28 07:00:46 +00:00
|
|
|
// advanceTo another node.
|
|
|
|
I.advanceTo(200);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(200u, I.start());
|
|
|
|
EXPECT_EQ(205u, I.stop());
|
|
|
|
|
2010-12-03 19:02:00 +00:00
|
|
|
// Close the gap left, no coalescing.
|
|
|
|
I.setStart(196);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(196u, I.start());
|
|
|
|
EXPECT_EQ(205u, I.stop());
|
|
|
|
EXPECT_EQ(20u, I.value());
|
|
|
|
|
|
|
|
// Change value, no coalescing.
|
|
|
|
I.setValue(0);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(196u, I.start());
|
|
|
|
EXPECT_EQ(205u, I.stop());
|
|
|
|
EXPECT_EQ(0u, I.value());
|
|
|
|
|
|
|
|
// Change value, now coalescing.
|
|
|
|
I.setValue(19);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(190u, I.start());
|
|
|
|
EXPECT_EQ(205u, I.stop());
|
|
|
|
EXPECT_EQ(19u, I.value());
|
|
|
|
|
|
|
|
// Close the gap, now coalescing.
|
|
|
|
I.setValue(18);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
I.setStart(186);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(180u, I.start());
|
|
|
|
EXPECT_EQ(205u, I.stop());
|
|
|
|
EXPECT_EQ(18u, I.value());
|
|
|
|
|
2010-11-27 22:56:53 +00:00
|
|
|
// Erase from the front.
|
2010-11-28 07:00:46 +00:00
|
|
|
I = map.begin();
|
2010-11-27 22:56:53 +00:00
|
|
|
for (unsigned i = 0; i != 20; ++i) {
|
|
|
|
I.erase();
|
|
|
|
EXPECT_TRUE(I == map.begin());
|
|
|
|
EXPECT_FALSE(map.empty());
|
|
|
|
EXPECT_EQ(I.start(), map.start());
|
|
|
|
EXPECT_EQ(995u, map.stop());
|
|
|
|
}
|
|
|
|
|
2010-11-19 23:28:57 +00:00
|
|
|
// Test clear() on branched map.
|
|
|
|
map.clear();
|
|
|
|
EXPECT_TRUE(map.empty());
|
|
|
|
EXPECT_TRUE(map.begin() == map.end());
|
2010-11-19 04:47:19 +00:00
|
|
|
}
|
|
|
|
|
2010-11-26 06:54:20 +00:00
|
|
|
// Branched, high, non-coalescing tests.
|
|
|
|
TEST(IntervalMapTest, Branched2) {
|
2010-12-03 19:02:00 +00:00
|
|
|
UUMap::Allocator allocator;
|
|
|
|
UUMap map(allocator);
|
2010-11-26 06:54:20 +00:00
|
|
|
|
|
|
|
// Insert enough intervals to force a height >= 2 tree.
|
|
|
|
for (unsigned i = 1; i < 1000; ++i)
|
|
|
|
map.insert(10*i, 10*i+5, i);
|
|
|
|
|
|
|
|
// Tree limits.
|
|
|
|
EXPECT_FALSE(map.empty());
|
|
|
|
EXPECT_EQ(10u, map.start());
|
|
|
|
EXPECT_EQ(9995u, map.stop());
|
|
|
|
|
|
|
|
// Tree lookup.
|
|
|
|
for (unsigned i = 1; i < 1000; ++i) {
|
|
|
|
EXPECT_EQ(0u, map.lookup(10*i-1));
|
|
|
|
EXPECT_EQ(i, map.lookup(10*i));
|
|
|
|
EXPECT_EQ(i, map.lookup(10*i+5));
|
|
|
|
EXPECT_EQ(0u, map.lookup(10*i+6));
|
|
|
|
}
|
|
|
|
|
|
|
|
// Forward iteration.
|
2010-12-03 19:02:00 +00:00
|
|
|
UUMap::iterator I = map.begin();
|
2010-11-26 06:54:20 +00:00
|
|
|
for (unsigned i = 1; i < 1000; ++i) {
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(10*i, I.start());
|
|
|
|
EXPECT_EQ(10*i+5, I.stop());
|
|
|
|
EXPECT_EQ(i, *I);
|
|
|
|
++I;
|
|
|
|
}
|
|
|
|
EXPECT_FALSE(I.valid());
|
|
|
|
EXPECT_TRUE(I == map.end());
|
|
|
|
|
|
|
|
// Backwards iteration.
|
|
|
|
for (unsigned i = 999; i; --i) {
|
|
|
|
--I;
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(10*i, I.start());
|
|
|
|
EXPECT_EQ(10*i+5, I.stop());
|
|
|
|
EXPECT_EQ(i, *I);
|
|
|
|
}
|
|
|
|
EXPECT_TRUE(I == map.begin());
|
|
|
|
|
2010-11-28 07:00:46 +00:00
|
|
|
// Test advanceTo in same node.
|
|
|
|
I.advanceTo(20);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(20u, I.start());
|
|
|
|
EXPECT_EQ(25u, I.stop());
|
|
|
|
|
|
|
|
// advanceTo sibling leaf node.
|
|
|
|
I.advanceTo(200);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(200u, I.start());
|
|
|
|
EXPECT_EQ(205u, I.stop());
|
|
|
|
|
|
|
|
// advanceTo further.
|
|
|
|
I.advanceTo(2000);
|
|
|
|
ASSERT_TRUE(I.valid());
|
|
|
|
EXPECT_EQ(2000u, I.start());
|
|
|
|
EXPECT_EQ(2005u, I.stop());
|
|
|
|
|
2010-11-26 06:54:20 +00:00
|
|
|
// Test clear() on branched map.
|
|
|
|
map.clear();
|
|
|
|
EXPECT_TRUE(map.empty());
|
|
|
|
EXPECT_TRUE(map.begin() == map.end());
|
|
|
|
}
|
|
|
|
|
2010-11-27 21:12:36 +00:00
|
|
|
// Random insertions, coalescing to a single interval.
|
|
|
|
TEST(IntervalMapTest, RandomCoalescing) {
|
2010-12-03 19:02:00 +00:00
|
|
|
UUMap::Allocator allocator;
|
|
|
|
UUMap map(allocator);
|
2010-11-27 21:12:36 +00:00
|
|
|
|
|
|
|
// This is a poor PRNG with maximal period:
|
|
|
|
// x_n = 5 x_{n-1} + 1 mod 2^N
|
|
|
|
|
|
|
|
unsigned x = 100;
|
|
|
|
for (unsigned i = 0; i != 4096; ++i) {
|
|
|
|
map.insert(10*x, 10*x+9, 1);
|
|
|
|
EXPECT_GE(10*x, map.start());
|
|
|
|
EXPECT_LE(10*x+9, map.stop());
|
|
|
|
x = (5*x+1)%4096;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Map should be fully coalesced after that exercise.
|
|
|
|
EXPECT_FALSE(map.empty());
|
|
|
|
EXPECT_EQ(0u, map.start());
|
|
|
|
EXPECT_EQ(40959u, map.stop());
|
|
|
|
EXPECT_EQ(1, std::distance(map.begin(), map.end()));
|
|
|
|
|
|
|
|
}
|
|
|
|
|
2010-11-19 04:47:19 +00:00
|
|
|
} // namespace
|