Skip to content

Commit

Permalink
Merge pull request #1528 from IkkiOcean/bentley
Browse files Browse the repository at this point in the history
Added Bentley-Ottmann Algorithm for Segment Intersection
  • Loading branch information
pankaj-bind authored Oct 31, 2024
2 parents 8fc591e + 0a735d9 commit b61d24e
Show file tree
Hide file tree
Showing 2 changed files with 101 additions and 0 deletions.
48 changes: 48 additions & 0 deletions Miscellaneous Algorithms/Bentley-Ottmann Algorithm /README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
# Bentley-Ottmann Algorithm

## Overview

The Bentley-Ottmann Algorithm is an efficient algorithm for finding all intersections between line segments in a plane. It operates in O((n + k) log n) time complexity, where *n* is the number of segments and *k* is the number of intersections. Unlike brute-force approaches that require checking every pair of segments, the Bentley-Ottmann algorithm reduces unnecessary comparisons by focusing on potential intersection points.

## Key Features

- **Efficient Computation**: Reduces the number of comparisons, especially effective for large datasets.
- **Event-driven Mechanism**: Uses a sweep line and event queue for optimal event handling.
- **Real-time Intersections**: Capable of handling intersections as they occur without processing the entire dataset beforehand.

## How It Works

The Bentley-Ottmann algorithm operates by sweeping a vertical line from left to right across a plane with multiple line segments. Events are generated based on the following:

1. **Left Endpoint**: When the line encounters the left endpoint of a segment, it adds that segment to an active list.
2. **Right Endpoint**: When the line encounters the right endpoint of a segment, it removes the segment from the active list.
3. **Intersection Point**: When the sweep line detects intersections between segments in the active list, it identifies them and logs the intersection.

The algorithm uses a priority queue for managing events (either endpoints or intersection points) and a balanced tree for keeping track of active segments in the sweep line order.

## Usage

The algorithm can be used to identify intersections in a variety of applications, such as:

- Geographic Information Systems (GIS) to detect overlapping roads or boundaries.
- Computer Graphics for handling visible surfaces or creating complex polygonal shapes.
- Robotics for path planning, obstacle avoidance, or collision detection.

## Complexity

- **Time Complexity**: \(O((n + k) \log n)\), where \(n\) is the number of line segments and \(k\) is the number of intersection points.
- **Space Complexity**: \(O(n + k)\) to store segments and intersections.

### Explanation

1. **Point Struct**: Represents a point in the 2D plane.
2. **Segment Struct**: Represents a line segment with two endpoints.
3. **orientation Function**: Determines the orientation of three points.
4. **doIntersect Function**: Checks if two line segments intersect.
5. **findIntersections Function**: Loops over all segments and detects intersections by calling `doIntersect`.

This is a simplified version of the Bentley-Ottmann Algorithm, designed to illustrate core concepts without complex data structures. For larger datasets, implementing a sweep line with event queue and balanced trees would be beneficial.

## Conclusion

The Bentley-Ottmann Algorithm provides a powerful and efficient approach for finding intersections among line segments. Its event-driven, sweep line methodology avoids excessive comparisons and operates effectively even in large datasets. This algorithm is valuable in computational geometry, computer graphics, and various fields that require accurate detection of segment intersections.
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
#include <stdio.h>
#include <stdlib.h>

typedef struct Point {
double x, y;
} Point;

typedef struct Segment {
Point start, end;
} Segment;

// Utility function to determine the orientation of three points
int orientation(Point p, Point q, Point r) {
double val = (q.y - p.y) * (r.x - q.x) - (q.x - p.x) * (r.y - q.y);
return (val == 0) ? 0 : (val > 0) ? 1 : 2;
}

// Function to check if two line segments intersect
int doIntersect(Segment s1, Segment s2) {
int o1 = orientation(s1.start, s1.end, s2.start);
int o2 = orientation(s1.start, s1.end, s2.end);
int o3 = orientation(s2.start, s2.end, s1.start);
int o4 = orientation(s2.start, s2.end, s1.end);

if (o1 != o2 && o3 != o4) return 1;
return 0;
}

// Event handler to find all intersections
void findIntersections(Segment segments[], int n) {
printf("Intersections:\n");
for (int i = 0; i < n; i++) {
for (int j = i + 1; j < n; j++) {
if (doIntersect(segments[i], segments[j])) {
printf("Intersection between segment %d and segment %d\n", i + 1, j + 1);
}
}
}
}

int main() {
Segment segments[] = {
{{1, 1}, {4, 4}},
{{1, 8}, {2, 4}},
{{3, 3}, {4, 1}},
{{4, 0}, {4, 5}}
};

int n = sizeof(segments) / sizeof(segments[0]);
findIntersections(segments, n);

return 0;
}

0 comments on commit b61d24e

Please sign in to comment.