If these two conditions are met then a square grid of side length \u0394 may be a

If these two conditions are met then a square grid of

This preview shows page 5 - 7 out of 11 pages.

small. If these two conditions are met, then a square grid of side length Δ may be a good way to store your data. Here is how this works. First, for each of your objects, compute its axis-aligned bounding box. We can efficiently determine which cells of the grid are overlapped by this bounding box as follows. Let p and q denote the bounding box’s lower-left and upper-right corners (see Fig. 4(a)). Compute the cells of the grid that contain these points (see Fig. 4(b)). Then store a pointer to the object in all the grid cells that lie in the rectangle defined by these two cells (see Fig. 4(c)). Note that this is not perfect, since the object may be associated with grid cells that it does not actually intersect. This increases the space of the data structure, but it does not compromise the data structure’s correctness. (a) (b) (c) Δ Δ q p i j Δ q p i j Fig. 4: Storing an object in a grid. Computing the indices of the grid cell that contain a given point is a simple exercise in integer arithmetic. For example, if p = ( p x , p y ), then let j = j p x Δ k and i = j p y Δ k . Then, the point p lies within the grid cell G [ i, j ]. If the diameter of most of the objects is not significantly larger than Δ, then each object will only be associated with a constant number of grid cells. If the density of objects is not too Lecture 8 5 Spring 2018
Image of page 5
CMSC 425 Dave Mount & Roger Eastman high, then each grid square will only need to store a constant number of pointers. Thus, if the above assumptions are satisfied then the data structure will be relatively space efficient. Storing a Grid: As we have seen, a grid consists of a collection of cells where each cell stores a set of pointers to the objects that overlap this cell (or at least might overlap this cell). How do we store these cells? Here are a few ideas. d -dimensional array: The simplest implementation is to allocate a d -dimensional array that is sufficiently large to handle all the cells of your grid. If the distribution of objects is relatively uniform, then it is reasonable to believe that a sizable fraction of the cells will be nonempty. On the other hand, if the density is highly variable, there may be many empty cells. This approach will waste space. Hash map: Each cell is identified by its indices, ( i, j ) for a 2-dimensional grid or ( i, j, k ) for the 3-dimensional grid. Treat these indices like a key into a hash map. Whenever a new object o is entered into some cell ( i, j ), we access the hash map to see whether this cell exists. If not, we generate a new cell object and add it to the hash map under the key ( i, j ). If so, we add a pointer to o into this hash map entry. Linear allocation: Suppose that we decide to adopt an array allocation. A straightforward implementation of the d -dimensional array will result in a memory layout according to how your compiler chooses to allocate arrays, typically in what is called row-major order (see Fig. 5(a)). For example, if there are N columns, then the element ( i, j ) is mapped to index i · N + j in row-major order.
Image of page 6
Image of page 7

You've reached the end of your free preview.

Want to read all 11 pages?

  • Spring '17
  • Geometry, Fig., Roger Eastman, Dave Mount, axis-aligned bounding boxes

  • Left Quote Icon

    Student Picture

  • Left Quote Icon

    Student Picture

  • Left Quote Icon

    Student Picture