Giter Club home page Giter Club logo

isect_segments-bentley_ottmann's Introduction

Poly Point Intersections

This is a single-file, Python3 implementation of the Bentley-Ottmann sweep-line algorithm for listing all intersections in a set of line segments.

This was initially based on the excellent CompGeom library, but aims to be portable & self-contained, (move to other lower languages such as C & C++).

https://cloud.githubusercontent.com/assets/1869379/10564349/753dd564-75fc-11e5-8e99-08530e6f6ef0.png

Testcase with showing all 73002 intersections from 14880 segments.

Motivation

At the time of writing, all the open-source implementation of Bentley-Ottmann's sweep-line I couldn't find a good reference implementation which performed well and could be reused or ported to different environments.

So this is my attempt to write a reference implementation with comprehensive tests.

Existing Implementations

  • CompGeom (Java).

  • CGAL SweepLine (C++).

    Not Bentley-Ottmann strictly speaking, but the method is very similar.

  • The geomalgorithms.com, while a great introduction, and frequently linked to as a reference, it only detects weather the polygon is self-intersecting or not.

Goals

  • Keep the library small, robust & reusable.

  • Use mainly language-agnostic features.

    (Even though classes are used, theres no problem moving this to a language without OO).

Usage

poly_point_isect is a single Python module, exposing 2 functions.

isect_polygon(points)
Where points are a sequence of number pairs.
isect_segments(segments)
Where segments is list of point-pairs.

Both return a list of intersections.

Example:

# Show the result of a simple bow-tie quad
import poly_point_isect
poly = (
    (1.0, 0.0),
    (0.0, 1.0),
    (0.0, 0.0),
    (1.0, 1.0),
    )
isect = poly_point_isect.isect_polygon(poly)
print(isect)
# [(0.5, 0.5)]

There are also: isect_polygon_include_segments(points) and isect_segments_include_segments(segments), versions of the functions described above which return a tuple for each intersection: (point, list_of_segments) so you can find which segments belong to an intersection.

Details

  • Permissive MIT license.

    Note that both bintrees and CompGeom are MIT Licensed too.

  • Written in Python3 and runs in PyPy as well.

  • Runs in vanilla Python without any dependencies.

  • Uses bintrees Python module, with modifications to support a custom comparator function. Also removed some unused code.

    Note

    Using another binary-tree library shouldn't be a problem as long as you can override its comparison. Ideally allow passing a custom argument too (as is done here), to avoid using globals to access the sweep-line.

  • Includes tests for:

    • Intersecting segments.
    • Non intersecting segments.
    • Degenerate segments (overlapping & zero length)

    Test output can be optionally written to SVG files, see: tests/data_svg/ directory.

Known Limitations

For the purpose of this section, errors in detecting intersections are defined by any discrepancy with the result compared to testing every segment against every other segment.

Sweep Line Step-Size

Very small step sizes over near-vertical lines can cause errors (note that _exactly_ vertical lines are supported but have to be handled separately).

So far I didn't find a good general solution to this, though there are some ways to work-around the problem.

One way to resolve the problem is to use higher precision calculation for the sweep-line then the input data.

In my own tests I found for double precision floating point, ensuring at least 4e-06 between steps gives stable results * (rounding the input segments X axis to 5 decimal places).

* Checked with the included test-set at 3.6e-06 degree rotation increments from the initial rotation.

Further Work

  • More tests.
  • More test variations (different scales, rotations).

isect_segments-bentley_ottmann's People

Contributors

ideasman42 avatar nedbat avatar stephenmcd avatar

Watchers

James Cloos avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.