You are on page 1of 4

Data Structures Homework 7 Quad Trees

Overview
This assignment is due Tuesday, April 24 at 11:59:59pm and is worth 120 points toward your homework grade. Many software systems in graphics, robotics, games, geographic information systems, and computer vision require the use of spatial data structures to store and access positional information eciently. No one wants to have to search through information located in California for data about upstate New York! This project investigates one of these spatial data structures, a quad tree. A quad tree covers a rectangular region bounded by xmin x < xmax , ymin y < ymax . The four values xmin , xmax , ymin and ymax are xed when the quadtree is rst constructed. Each node of a quadtree covers a rectangular region, and has 0 or 4 children, 0 if it is a leaf and 4 if it is an internal node. If a node covers the region x0 x < x1 and y0 y < y1 , then, with xm = (x0 + x1 )/2, ym = (y0 + y1 )/2, the four children cover the rectangular subregions x0 x < xm , y0 y < xm (node NW), xm x < x1 , y0 y < xm (node NE), x0 x < xm , ym y < y1 (node SW), and xm x < x1 , ym y < y1 (node SE). (Note that the origin of graphics coordinate systems is almost always to the upper left with x increasing left-to-right and y increasing top-to-bottom.) For this homework, the values stored in the quadtree will be point locations (x, y). Only leaf nodes actually store point locations. The driving issue in the formation of a quadtree is when to split a leaf node to form four children. Initially, the root node is a leaf node and contains no children. Each point added to the tree is stored in the root, up until there would be more than k0 points where k0 is a parameter to the quadtree data structure. (Typically, k0 is a relatively small number, perhaps 3-5, but could be much larger.) At this time, four children nodes, covering the four quadrants, NW, NE, SW, SE, are created and the points are then re-assigned to the children nodes according to which sub-rectangle they are in. If all points are in only one of the quadrants, this splitting will continue recursively, but only in that quadrant. When one or more points are removed, it is possible that leaf nodes will need to be removed and points merged back into the parent. In particular, after points are removed, if the four children of an internal node contain k0 points, then these four children are deleted (all them will be leaf nodes), and the points are stored at the node. This can continue recursively back up the tree. We will run nd and erase operations on our quadtree by searching in circular regions. This will proceed recursively down the quadtree, but the recursion down a subtree should not proceed if there is no possibility of an intersection between a circle and the rectangular region covered by the node. (Write a function to test this you will need to call it from several places. The simplest way to do it is to test the square that bounds the circle with a nodes rectangle; not an exact solution, but good enough.) A point that is exactly on

the boundary of the circle is NOT considered inside the circle we will not test for this, however.

Example
Suppose our quadtree is bounded by x0 = 0, x1 = 160, y0 = 60 and y1 = 180, with k0 = 3 and weve inserted the following points: 10, 70 42, 70 42, 75 150, 175 63.3, 85 38, 76 Then a schematic of the quadtree looks like.
!" %!" $!" #!" &%!"

'!"

&(!"

&#!"

The root nodes region has been split into four children. The NE and SW children of the root are both empty, while the SE child has one point. All three of these are leaf nodes. On the other hand, the NW child of the root contains ve points and has been split into four children again, with the SW and SE children of this node being empty, and the NW and NE children containing 2 and 3 points, respectively. The addition of another point such as 44,78 would cause the NE child of the NW child of the root to split into four children. (We STRONGLY RECOMMEND that you draw pictures like this, by hand, to help you visualize how your program is behaving.) Running a find operation with a circle centered at 41, 72 and radius 5.5 would return three points, two of them taken from one leaf and the third from a dierent leaf. Running erase with a circle at 43, 73.5 and radius 3 would cause two points to be removed and would cause the NW neighbor of the root to eliminate its children, gathering the remaining points back into its point vector, and becoming a leaf node again. On the other hand, making this circle have a radius of 7 would cause three points to be removed, and two levels of collapse would occur, resulting in the quad tree just having a root node.

What You Need To Do


Your only job on this assignment is to implement the QuadTree class. We have provided you with a main program to test its functionality, a simple version of the test code that would exist as part of a production software system. We will test using a more sophisticated main program you will not see in advance, so for your own development eort you should create more sophisticated tests. We have provided the public interface to the QuadTree class. Do not change the form of the function calls. You must implement the class, including the private member variables you decide to add. You may dene additional member functions, both public and private, and you may dene other classes (including a node class, of course). See the documentation in the header le provided and the example output for exact details of how the functions should behave.

Suggestions
Follow the form of the ds_set class, which has public member functions that call private member functions to do the actual work. You do NOT need an iterator class. The quad tree node class is more sophisticated than the binary search tree node class, and includes at least four pointers, the x and y bounds on the region covered by the node, and a vector of points. You may add other member variables to this class. You are welcome to make all member variables of this class public. Remember that the vector of points is always empty if the children pointer are null. An empty quadtree one that stores no points always has at least a root node. This root node stores the bounds on the region covered by the quadtree. After writing the quadtree node class, start with the insert function. Next, write the print leaf function (see the .h le and the example main program), which shows the properties of the leaf node containing a given point, and write the print tree function, which shows the structure of the tree. We will use these functions to test the correctness of your implementation. Thoroughly test insert, print leaf and print tree even more thoroughly than our example main function does before proceeding. We recommend that you rst implement erase without collapsing nodes, and then add the node collapsing. If you cant get node collapsing to work, submit your code without it. As dened here, the quadtree class will go into an innite recursion if more k0 copies of exactly the same point are inserted. You do not need to worry about this case. In fact, we will not give you repeated points. As an aside, if your insert function does not work quite right, you might create a bug that causes an innite recursion to occur thats what I found with the initial version of my own code when I started to debug it!

What to Submit
Submit the main function we provided together with the point class (also provided, although you are welcome to add to it) and your classes for the quadtree implementation. Please also submit a readme.txt le. The template is provided.

You might also like