K Dimensional Tree In C++

A data structure is called a K-dimensional tree , or simply a K-D tree . It is made for effective spatial searches in K-dimensional domains. It is a multi-dimensional generalization of the binary search tree. K-D trees are used in a variety of domains, including computer graphics, nearest-neighbor analysis, and data mining. They are very helpful for tackling a variety of computational geometry issues, such as range search and nearest neighbor search.

Properties and Structure:

  • Each node in a K-D tree represents a point in the K-dimensional space .
  • Each node contains two children: a left child and a right child , arranged in a binary tree structure.
  • At every level of the tree, points are split alternating along several dimensions.
  • The selection of the dividing dimension at each level might be based on several heuristics, such as choosing the dimension with the greatest spread or cycling through the different dimensions.
  • Operations:

  • Insertion: To add a new point to the K-D tree , one must navigate the tree to choose the best location for the new node by the splitting rule.
  • Search: K-D trees allow several search functions, such as range search, which locates all points inside a given range, and nearest neighbor search, which locates the point in the tree that is closest to a particular query point.
  • Deletion: Carefully examining the tree structure and rearranging the tree as necessary are required when removing a node from the K-D tree while preserving its attributes.
  • Applications:

K-D trees are widely used in many different fields, such as:

  • Applications such as databases and data mining use nearest neighbor search.
  • Geographic information systems (GIS) use spatial indexing.
  • Effective range search for geographical information systems and computational geometry.
  • To produce scenes more quickly in computer graphics by speeding up ray tracing algorithms .
  • Code:

Let's take an example to illustrate the K-Dimensional tree in C++:

Example

#include <iostream>
#include <vector>
#include <algorithm>
#include <cmath>
struct Point {
    std::vector<double> coords;
};
struct Node {
    Poincpp tutorial;
    Node* left;
    Node* right;
};
// Function to create a new node
Node* newNode(Poincpp tutorial) {
    Node* node = new Node;
    node->point = point;
    node->left = node->right = nullptr;
    return node;
}
// Function to calculate the distance between two points
double distance(Point a, Point b) 
{
    double dist = 0;
    for (size_t i = 0; i < a.coords.size(); ++i) 
    {
        dist += (a.coords[i] - b.coords[i]) * (a.coords[i] - b.coords[i]);
    }
    return std::sqrt(dist);
}
// Function to insert a new node into the K-D tree
Node* insertNode(Node* root, Poincpp tutorial, unsigned depth)
{
    if (root == nullptr) 
    {
        return newNode(point);
    }
    unsigned k = point.coords.size();
    unsigned cd = depth % k;
    if (point.coords[cd] < (root->point.coords[cd])) 
    {
        root->left = insertNode(root->left, point, depth + 1);
    } 
    else
    {
        root->right = insertNode(root->right, point, depth + 1);
    }
    return root;
}
// Function to find the nearest neighbor
Node* findNearestNeighbor(Node* root, Poincpp tutorial, unsigned depth, Node* best, double& bestDist)
{
    if (root == nullptr) return best;
    double dist = distance(root->point, point);
    if (dist < bestDist) 
    {
        bestDist = dist;
        best = root;
    }
    unsigned k = point.coords.size();
    unsigned cd = depth % k;
    if (point.coords[cd] < root->point.coords[cd])
    {
        best = findNearestNeighbor(root->left, point, depth + 1, best, bestDist);
        if (point.coords[cd] + bestDist >= root->point.coords[cd]) 
        {
            best = findNearestNeighbor(root->right, point, depth + 1, best, bestDist);
        }
    } 
    else
    {
        best = findNearestNeighbor(root->right, point, depth + 1, best, bestDist);
        if (point.coords[cd] - bestDist <= root->point.coords[cd]) 
        {
            best = findNearestNeighbor(root->left, point, depth + 1, best, bestDist);
        }
    }
    return best;
}
// Function to perform a range search and return points within a specified range
void range_Search(Node* root, Point low, Point high, unsigned depth) 
{
    if (root == nullptr) return;
    unsigned k = low.coords.size();
    unsigned cd = depth % k;
    if (root->point.coords[cd] >= low.coords[cd])
    {
        range_Search(root->left, low, high, depth + 1);
    }
    if (root->point.coords[cd] <= high.coords[cd] && root->point.coords[cd] >= low.coords[cd])
    {
        // This point is within the range
        std::cout << "Point: [";
        for (size_t i = 0; i < k - 1; ++i) 
        {
            std::cout << root->point.coords[i] << ", ";
        }
        std::cout << root->point.coords[k - 1] << "]\n";
    }
    if (root->point.coords[cd] <= high.coords[cd]) 
    {
        range_Search(root->right, low, high, depth + 1);
    }
}
// Sample usage of the K-D tree
int main() 
{
    Node* root = nullptr;
    std::vector<Point> points = { { {3, 6} }, { {17, 15} }, { {13, 15} }, { {6, 12} }, { {9, 1} }, { {2, 7} }, { {10, 19} } };
    for (const auto& point: points)
    {
        root = insertNode(root, point, 0);
    }
    // Perform nearest neighbor search
    Point queryPoint = { {7, 10} };
    double bestDist = std::numeric_limits<double>::max();
    Node* nearest = findNearestNeighbor(root, queryPoint, 0, nullptr, bestDist);
    std::cout << "Nearest Neighbor: [";
    for (size_t i = 0; i < queryPoint.coords.size() - 1; ++i)
    {
        std::cout << nearest->point.coords[i] << ", ";
    }
    std::cout << nearest->point.coords[queryPoint.coords.size() - 1] << "]\n";
    // Perform range search
    Point low = { {4, 5} };
    Point high = { {14, 14} };
    std::cout << "Points within range:\n";
    range_Search(root, low, high, 0);
    return 0;
}

Output:

Output

Nearest Neighbor: [6, 12]
Points within range:
Point: [6, 12]
  • Construction of a 2D point K-D tree .
  • Find the closest neighbor for a specific query point.
  • Use range search to locate points within a given range.

Input Required

This code uses input(). Please provide values below: