WIP (quad tree)

This commit is contained in:
Matthias Koefferlein 2025-03-16 13:56:16 +01:00
parent 54b5d9f5d6
commit 5c8e0539ee
2 changed files with 249 additions and 5 deletions

View File

@ -44,16 +44,77 @@ public:
quad_tree_node (const point_type &center)
: m_split (false), m_center (center)
{
for (unsigned int i = 0; i < 4; ++i) {
m_q [i] = 0;
}
init ();
}
~quad_tree_node ()
{
clear ();
}
quad_tree_node (const quad_tree_node &other)
: m_split (false), m_center (center)
{
init ();
operator= (other);
}
quad_tree_node &operator= (const quad_tree_node &other)
{
if (this != &other) {
clear ();
m_split = other.m_split;
m_center = other.m_center;
m_objects = other.m_objects;
for (unsigned int i = 0; i < 4; ++i) {
if (other.m_q[i]) {
m_q[i] = other.m_q[i]->clone ();
}
}
}
return *this;
}
quad_tree_node (quad_tree_node &&other)
{
init ();
swap (other);
}
quad_tree_node &operator= (quad_tree_node &&other)
{
swap (other);
return *this;
}
void swap (quad_tree_node &other)
{
if (this != &other) {
std::swap (m_center, other.m_center);
std::swap (m_split, other.m_split);
m_objects.swap (other.m_objects);
for (unsigned int i = 0; i < 4; ++i) {
std::swap (m_q[i], other.m_q[i]);
}
}
}
quad_tree_node *clone () const
{
quad_tree_node *node = new quad_tree_node (m_center);
*node = *this;
return node;
}
void clear ()
{
m_objects.clear ();
m_split = false;
for (unsigned int i = 0; i < 4; ++i) {
delete m_q [i];
m_q [i] = 0;
if (m_q[i]) {
delete m_q[i];
}
m_q[i] = 0;
}
}
@ -163,6 +224,13 @@ private:
quad_tree_node *m_q [4];
objects_vector m_objects;
void init ()
{
for (unsigned int i = 0; i < 4; ++i) {
m_q[i] = 0;
}
}
int quad_for (const box_type &box) const
{
int sx = coord_traits::less (box.right (), m_center.x ()) ? 0 : (coord_traits::less (m_center.x (), box.left ()) ? 1 : -1);
@ -521,6 +589,47 @@ public:
// .. nothing yet ..
}
quad_tree (const quad_tree &other)
: m_root (point_type ())
{
operator= (other);
}
quad_tree &operator= (const quad_tree &other)
{
if (this != &other) {
m_root = other.m_root;
m_total_box = other.m_total_box;
}
return *this;
}
quad_tree (quad_tree &&other)
: m_root (point_type ())
{
swap (other);
}
quad_tree &operator= (quad_tree &&other)
{
swap (other);
return *this;
}
void clear ()
{
m_root.clear ();
m_total_box = box_type ();
}
void swap (quad_tree &other)
{
if (this != &other) {
m_root.swap (other.m_root);
std::swap (m_total_box, m_total_box);
}
}
bool empty () const
{
return m_root.empty ();

View File

@ -256,3 +256,138 @@ TEST(remove)
EXPECT_EQ (tree.levels (), size_t (1));
}
TEST(clear)
{
my_quad_tree tree;
tree.insert (db::DBox (-1, -2, 3, 4));
tree.insert (db::DBox (-1, -3, 3, 0));
tree.insert (db::DBox (-1, -3, -0.5, -2));
tree.insert (db::DBox (-1, -3, -0.5, 2));
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (find_all (tree), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
tree.clear ();
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (tree.empty (), true);
EXPECT_EQ (tree.size (), size_t (0));
EXPECT_EQ (tree.levels (), size_t (1));
EXPECT_EQ (find_all (tree), "");
}
TEST(copy)
{
my_quad_tree tree;
tree.insert (db::DBox (-1, -2, 3, 4));
tree.insert (db::DBox (-1, -3, 3, 0));
tree.insert (db::DBox (-1, -3, -0.5, -2));
tree.insert (db::DBox (-1, -3, -0.5, 2));
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (find_all (tree), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree.levels (), size_t (2));
my_quad_tree tree2 (tree);
tree.clear ();
EXPECT_EQ (tree2.check (), true);
EXPECT_EQ (find_all (tree2), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree2.levels (), size_t (2));
}
TEST(assign)
{
my_quad_tree tree;
tree.insert (db::DBox (-1, -2, 3, 4));
tree.insert (db::DBox (-1, -3, 3, 0));
tree.insert (db::DBox (-1, -3, -0.5, -2));
tree.insert (db::DBox (-1, -3, -0.5, 2));
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (find_all (tree), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree.levels (), size_t (2));
my_quad_tree tree2;
tree2 = tree;
tree.clear ();
EXPECT_EQ (tree2.check (), true);
EXPECT_EQ (find_all (tree2), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree2.levels (), size_t (2));
}
TEST(swap)
{
my_quad_tree tree;
tree.insert (db::DBox (-1, -2, 3, 4));
tree.insert (db::DBox (-1, -3, 3, 0));
tree.insert (db::DBox (-1, -3, -0.5, -2));
tree.insert (db::DBox (-1, -3, -0.5, 2));
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (find_all (tree), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree.levels (), size_t (2));
my_quad_tree tree2;
tree2.swap (tree);
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (tree.empty (), true);
EXPECT_EQ (find_all (tree), "");
EXPECT_EQ (tree.levels (), size_t (1));
EXPECT_EQ (tree2.check (), true);
EXPECT_EQ (find_all (tree2), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree2.levels (), size_t (2));
}
TEST(move)
{
my_quad_tree tree;
tree.insert (db::DBox (-1, -2, 3, 4));
tree.insert (db::DBox (-1, -3, 3, 0));
tree.insert (db::DBox (-1, -3, -0.5, -2));
tree.insert (db::DBox (-1, -3, -0.5, 2));
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (find_all (tree), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree.levels (), size_t (2));
my_quad_tree tree2;
tree2 = std::move (tree);
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (tree.empty (), true);
EXPECT_EQ (find_all (tree), "");
EXPECT_EQ (tree.levels (), size_t (1));
EXPECT_EQ (tree2.check (), true);
EXPECT_EQ (find_all (tree2), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree2.levels (), size_t (2));
}
TEST(move_ctor)
{
my_quad_tree tree;
tree.insert (db::DBox (-1, -2, 3, 4));
tree.insert (db::DBox (-1, -3, 3, 0));
tree.insert (db::DBox (-1, -3, -0.5, -2));
tree.insert (db::DBox (-1, -3, -0.5, 2));
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (find_all (tree), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree.levels (), size_t (2));
my_quad_tree tree2 (std::move (tree));
EXPECT_EQ (tree.check (), true);
EXPECT_EQ (tree.empty (), true);
EXPECT_EQ (find_all (tree), "");
EXPECT_EQ (tree.levels (), size_t (1));
EXPECT_EQ (tree2.check (), true);
EXPECT_EQ (find_all (tree2), "(-1,-2;3,4)/(-1,-3;-0.5,-2)/(-1,-3;-0.5,2)/(-1,-3;3,0)");
EXPECT_EQ (tree2.levels (), size_t (2));
}