Open In App

Grouping robots on cartesian plane

Last Updated : 04 Dec, 2023
Improve
Improve
Like Article
Like
Save
Share
Report

In a 2D array robots[][], and an integer value K, where robots[i][j] represent the position of a robot on the cartesian plan. The task is to count the number of minimum groups that are formed by the robots such that the distance between robots in a group should be <= K.

Note: If two robots, ‘a’ and ‘b’, belong to the same group, and ‘a’ and ‘d’ also belong to the same group, then ‘b‘ and ‘d’ are to be considered part of the same group as well.

Examples:

Input: robots[][] = {{13, -62}, {3, 3}, {2, 2}}, K = 2
Output: 2
Explanation: There are two groups.
1st group: {{2, 2}, {3, 3}}
2nd group: {{12, -62}}

Input: robots[][] = {{13, 26}, {14, 12}, {31, 12}, {14, 29}}, K = 2
Output: 3

Approach (Using Disjoint Set Union):

Initially, consider each robot as a separate and distinct group. Therefore, the initial count of separate groups is equal to ‘N’ (where ‘N’ represents the total number of robots in the robots[][] array). Create pairs of robots from the array ‘robots[][]’. Subsequently, check whether the distance between these robots is less than or equal to ‘K’. If this condition is true, combine the robots into a single group and decrease the count of separate groups by 1.

Steps to solve the problem:

  • Iterate over all pairs of robots positions, calculating the distance between them using the distance formula.
  • If the distance is less than or equal to ‘K‘, merge the two robots into one group and update the connected component count.
  • Return the count of connected components after processing all the pairs of robots.

Below is the implementation of the above approach:

C++




// C++ code to implement the approach
 
#include <bits/stdc++.h>
using namespace std;
 
// Function to find the parent of a node
int find(int x, vector<int>& parent)
{
    if (x == parent[x])
        return x;
 
    return parent[x] = find(parent[x], parent);
}
 
// Function to unite two sets
bool union1(int x, int y, vector<int>& parent,
            vector<int>& rank)
{
    int lx = find(x, parent);
    int ly = find(y, parent);
 
    // Condition of merging
    if (lx != ly) {
        if (rank[lx] > rank[ly]) {
            parent[ly] = lx;
        }
        else if (rank[lx] < rank[ly]) {
            parent[lx] = ly;
        }
        else {
            parent[lx] = ly;
            rank[ly] += 1;
        }
 
        // Return true for merging two
        // groups into one groups
        return true;
    }
 
    // Return false if robots are
    // already merged.
    return false;
}
 
// Function to count the number of groups
// formed after grouping the robots
int solve(vector<vector<int> >& robots, int k)
{
    int n = robots.size(),
 
        // cc is for number of
        // connected component
        cc = n;
 
    vector<int> parent(n), rank(n);
 
    for (int i = 0; i < n; i++) {
        parent[i] = i;
        rank[i] = 1;
    }
 
    // Iterate over all pairs of robot
    for (int i = 0; i < n; i++) {
        for (int j = i + 1; j < n; j++) {
 
            long long x1 = robots[i][0], y1 = robots[i][1];
            long long x2 = robots[j][0], y2 = robots[j][1];
 
            // Calculate the distance
            // between the robots
            long long x = (x2 - x1) * (x2 - x1)
                          + (y2 - y1) * (y2 - y1);
 
            // Check the given condition
            if (x * x <= k * k) {
 
                // Merge this pair of robots
                // into one group
                bool merge = union1(i, j, parent, rank);
 
                // If these robots are getting
                // merged then reduce the cc by 1;
                if (merge)
                    cc--;
            }
        }
    }
 
    return cc;
}
 
// Driver code
int main()
{
    vector<vector<int> > robots
        = { { 13, -62 }, { 3, 3 }, { 2, 2 } };
    int K = 2;
    int result = solve(robots, K);
 
    // Function Call
    cout << result << endl;
    return 0;
}


Java




import java.util.ArrayList;
import java.util.List;
 
public class RobotGroups {
 
    // Function to find the parent of a node
    static int find(int x, List<Integer> parent)
    {
        if (x == parent.get(x))
            return x;
 
        // Path compression: Set the parent of x to the root
        // to optimize future lookups
        parent.set(x, find(parent.get(x), parent));
        return parent.get(x);
    }
 
    // Function to unite two sets
    static boolean union(int x, int y, List<Integer> parent,
                         List<Integer> rank)
    {
        int lx = find(x, parent);
        int ly = find(y, parent);
 
        // Condition of merging
        if (lx != ly) {
            if (rank.get(lx) > rank.get(ly)) {
                parent.set(ly, lx);
            }
            else if (rank.get(lx) < rank.get(ly)) {
                parent.set(lx, ly);
            }
            else {
                parent.set(lx, ly);
                rank.set(ly, rank.get(ly) + 1);
            }
 
            // Return true for merging two groups into one
            // group
            return true;
        }
 
        // Return false if robots are already merged.
        return false;
    }
 
    // Function to count the number of groups formed after
    // grouping the robots
    static int solve(List<int[]> robots, int k)
    {
        int n = robots.size();
 
        // cc is for the number of connected components
        // (groups)
        int cc = n;
 
        List<Integer> parent = new ArrayList<>(n);
        List<Integer> rank = new ArrayList<>(n);
 
        for (int i = 0; i < n; i++) {
            parent.add(i);
            rank.add(1);
        }
 
        // Iterate over all pairs of robots
        for (int i = 0; i < n; i++) {
            for (int j = i + 1; j < n; j++) {
                long x1 = robots.get(i)[0],
                     y1 = robots.get(i)[1];
                long x2 = robots.get(j)[0],
                     y2 = robots.get(j)[1];
 
                // Calculate the distance between the robots
                long x = (x2 - x1) * (x2 - x1)
                         + (y2 - y1) * (y2 - y1);
 
                // Check the given condition
                if (x * x <= k * k) {
 
                    // Merge this pair of robots into one
                    // group
                    boolean merge
                        = union(i, j, parent, rank);
 
                    // If these robots are getting merged,
                    // then reduce the cc by 1
                    if (merge)
                        cc--;
                }
            }
        }
 
        return cc;
    }
 
    public static void main(String[] args)
    {
        List<int[]> robots = new ArrayList<>();
        robots.add(new int[] { 13, -62 });
        robots.add(new int[] { 3, 3 });
        robots.add(new int[] { 2, 2 });
 
        int K = 2;
        int result = solve(robots, K);
 
        // Function Call
        System.out.println(result);
    }
}


Python3




# Python Implementation
 
# Function to find the parent of a node
def find(x, parent):
    if x == parent[x]:
        return x
    parent[x] = find(parent[x], parent)
    return parent[x]
 
# Function to unite two sets
def union(x, y, parent, rank):
    lx = find(x, parent)
    ly = find(y, parent)
 
    # Condition of merging
    if lx != ly:
        if rank[lx] > rank[ly]:
            parent[ly] = lx
        elif rank[lx] < rank[ly]:
            parent[lx] = ly
        else:
            parent[lx] = ly
            rank[ly] += 1
 
        # Return True for merging two groups into one group
        return True
 
    # Return False if robots are already merged
    return False
 
# Function to count the number of groups formed after grouping the robots
def solve(robots, k):
    n = len(robots)
 
    # cc is for number of connected component
    cc = n
 
    parent = [0] * n
    rank = [0] * n
 
    for i in range(n):
        parent[i] = i
        rank[i] = 1
 
    # Iterate over all pairs of robots
    for i in range(n):
        for j in range(i + 1, n):
            x1, y1 = robots[i]
            x2, y2 = robots[j]
 
            # Calculate the distance between the robots
            x = (x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1)
 
            # Check the given condition
            if x * x <= k * k:
                # Merge this pair of robots into one group
                merge = union(i, j, parent, rank)
 
                # If these robots are getting merged then reduce the cc by 1
                if merge:
                    cc -= 1
 
    return cc
 
# Driver code
robots = [[13, -62], [3, 3], [2, 2]]
K = 2
result = solve(robots, K)
 
# Function Call
print(result)
 
# This code is contributed by Tapesh (tapeshdua420)


C#




using System;
using System.Collections.Generic;
 
public class RobotGroups
{
    // Function to find the parent of a node
    static int Find(int x, List<int> parent)
    {
        if (x == parent[x])
            return x;
 
        return parent[x] = Find(parent[x], parent);
    }
 
    // Function to unite two sets
    static bool Union(int x, int y, List<int> parent, List<int> rank)
    {
        int lx = Find(x, parent);
        int ly = Find(y, parent);
 
        // Condition of merging
        if (lx != ly)
        {
            if (rank[lx] > rank[ly])
                parent[ly] = lx;
            else if (rank[lx] < rank[ly])
                parent[lx] = ly;
            else
            {
                parent[lx] = ly;
                rank[ly] += 1;
            }
 
            // Return true for merging two groups into one group
            return true;
        }
 
        // Return false if robots are already merged.
        return false;
    }
 
    // Function to count the number of groups formed after grouping the robots
    static int Solve(List<List<int>> robots, int k)
    {
        int n = robots.Count;
 
        // cc is for number of connected component
        int cc = n;
 
        List<int> parent = new List<int>();
        List<int> rank = new List<int>();
 
        for (int i = 0; i < n; i++)
        {
            parent.Add(i);
            rank.Add(1);
        }
 
        // Iterate over all pairs of robot
        for (int i = 0; i < n; i++)
        {
            for (int j = i + 1; j < n; j++)
            {
                long x1 = robots[i][0], y1 = robots[i][1];
                long x2 = robots[j][0], y2 = robots[j][1];
 
                // Calculate the distance between the robots
                long x = (x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1);
 
                // Check the given condition
                if (x * x <= k * k)
                {
                    // Merge this pair of robots into one group
                    bool merge = Union(i, j, parent, rank);
 
                    // If these robots are getting merged then reduce the cc by 1
                    if (merge)
                        cc--;
                }
            }
        }
 
        return cc;
    }
 
    // Driver code
    public static void Main(string[] args)
    {
        List<List<int>> robots = new List<List<int>>
        {
            new List<int> { 13, -62 },
            new List<int> { 3, 3 },
            new List<int> { 2, 2 }
        };
        int K = 2;
        int result = Solve(robots, K);
 
        // Function Call
        Console.WriteLine(result);
    }
}


Javascript




// Function to find the root parent of a node in the disjoint set
function find(parent, x) {
    if (x === parent[x]) // If the node's parent is itself, it's the root parent
        return x;
 
    // Path compression: Update the parent of the node and return the root parent
    return parent[x] = find(parent, parent[x]);
}
 
// Function to unite two sets by their root parents
function union(x, y, parent, rank) {
    let lx = find(parent, x);
    let ly = find(parent, y);
 
    if (lx !== ly) {
        // Union by rank: Attach smaller rank tree under root of higher rank tree
        if (rank[lx] > rank[ly])
            parent[ly] = lx;
        else if (rank[lx] < rank[ly])
            parent[lx] = ly;
        else {
            parent[lx] = ly;
            rank[ly] += 1; // Increase rank if ranks are equal
        }
 
        return true; // Return true for successful union
    }
 
    return false; // Return false if nodes are already in the same set
}
 
// Function to solve the problem and count groups formed after grouping the robots
function solve(robots, k) {
    let n = robots.length;
    let cc = n; // cc is for the number of connected components (initially each robot is its own group)
    let parent = []; // Array to store parent of each node
    let rank = []; // Array to store rank of each node (for union by rank)
 
    // Initialization: Each node is its own parent and has rank 1
    for (let i = 0; i < n; i++) {
        parent.push(i);
        rank.push(1);
    }
 
    // Iterate over pairs of robots
    for (let i = 0; i < n; i++) {
        for (let j = i + 1; j < n; j++) {
            let [x1, y1] = robots[i];
            let [x2, y2] = robots[j];
            let x = (x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1);
 
            // Check the distance condition for grouping robots
            if (x * x <= k * k) {
                let merge = union(i, j, parent, rank);
                if (merge)
                    cc--; // Reduce the number of groups if robots are merged
            }
        }
    }
 
    return cc; // Return the count of groups formed
}
 
// Test case
let robots = [
    [13, -62],
    [3, 3],
    [2, 2]
];
let k = 2;
let result = solve(robots, k);
 
console.log(result); // Output the result


Output

2







Time Complexity: O(N2), where N is the number of robots in the given robots[][] array.
Auxiliary Space: O(N), for storing the parents and rank array in Union Find.



Similar Reads

Program to determine the quadrant of the cartesian plane
Given co-ordinates (x, y), determine the quadrant of the cartesian plane. Image_source : wikipedia.org Examples : Input : x = 1, y = 1 Output : lies in 1st quadrant Input : x = 0, y = 0 Output : lies at origin There are 9 conditions that needs to be checked to determine where does the points lies - If in first quadrant then, x &gt; 0 and y &gt; 0 I
6 min read
Find number of Polygons lying inside each given Polygons on Cartesian Plane
Given N non-intersecting nested polygons, and a 2D array arr[][] of pairs, where each cell of the array represents the coordinates of the vertices of a polygon. The task is to find the count of polygons lying inside each polygon. Examples: Input: N = 3, arr[][][] = {{{-2, 2}, {-1, 1}, {2, 2}, {2, -1}, {1, -2}, {-2, -2}}, {{-1, -1}, {1, -1}, {1, 1}}
10 min read
Maximizing Chocolates in Grid using 2 robots (Chocolates Pickup)
Given a 2D array grid[][] of size R X C, such that grid[i][j] represents the number of chocolates that you can collect from the (i, j) cell. We have two robots that can collect the chocolates: Robot #1 is located at the top-left corner (0, 0), and Robot #2 is located at the top-right corner (0, cols - 1). Return the maximum number of chocolates we
13 min read
What is Robots.Txt File | Importance, Role, and Impact on SEO
A Robots.Txt File is a simple text file that instructs web crawlers about which parts of a website are open for indexing and which should remain off-limits. Robots.Txt File, located in a website's root directory, guides search engine crawlers on what to index and what to ignore. It plays a crucial role in shaping a website's presence in search resu
11 min read
Cartesian Product of Two Sets
Let A and B be two sets, Cartesian productA × B is the set of all ordered pair of elements from A and B A × B = {{x, y} : x ? A, y ? B} Let A = {a, b, c} and B = {d, e, f} The Cartesian product of two sets is A x B = {a, d}, {a, e}, {a, f}, {b, d}, {b, e}, {b, f}, {c, d}, {c, e}, {c, f}}A has 3 elements and B also has 3 elements. The Cartesian Prod
5 min read
Cartesian tree from inorder traversal | Segment Tree
Given an in-order traversal of a cartesian tree, the task is to build the entire tree from it. Examples: Input: arr[] = {1, 5, 3} Output: 1 5 3 5 / \ 1 3 Input: arr[] = {3, 7, 4, 8} Output: 3 7 4 8 8 / 7 / \ 3 4 Approach: We have already seen an algorithm here that takes O(NlogN) time on an average but can get to O(N2) in the worst case.In this art
13 min read
Program to convert polar co-ordinates to equivalent cartesian co-ordinates
Given two integers r and ? (in degree) representing polar coordinates of a point (r, ?), the task is to find the Cartesian coordinates of the given point. Examples: Input: r = 1.4142, ? = 45Output: 1.000, 1.000 Input: r = 3, ? = 30Output: 2.598, 1.500 Approach: Let the cartesian coordinates of the point be (x, y). The polar coordinates and the Cart
4 min read
Chart.js Cartesian Axes
Axes play a crucial role in Chart.js, providing context, labels, and scaling to enhance the informativeness and visual appeal of the charts. Axes apply to various types of charts, including line charts, bar charts, radar charts, and more. Types of AxesCartesian axes: Cartesian axes are the traditional x and y axes commonly used in line charts, bar
4 min read
Cartesian Tree
A Cartesian tree is a tree data structure created from a set of data that obeys the following structural invariants: The tree obeys in the min (or max) heap property - each node is less (or greater) than its children.An inorder traversal of the nodes yields the values in the same order in which they appear in the initial sequence. Suppose we have a
16 min read
Number of possible Triangles in a Cartesian coordinate system
Given n points in a Cartesian coordinate system. Count the number of triangles formed. Examples: Input : point[] = {(0, 0), (1, 1), (2, 0), (2, 2) Output : 3 Three triangles can be formed from above points. A simple solution is to check if the determinant of the three points selected is non-zero or not. The following determinant gives the area of a
7 min read