using System.Collections; namespace GisSharpBlog.NetTopologySuite.Index.Sweepline { /// /// A sweepline implements a sorted index on a set of intervals. /// It is used to compute all overlaps between the interval in the index. /// public class SweepLineIndex { private ArrayList events = new ArrayList(); private bool indexBuilt; // statistics information private int nOverlaps; /// /// /// public SweepLineIndex() { } /// /// /// /// public void Add(SweepLineInterval sweepInt) { SweepLineEvent insertEvent = new SweepLineEvent(sweepInt.Min, null, sweepInt); events.Add(insertEvent); events.Add(new SweepLineEvent(sweepInt.Max, insertEvent, sweepInt)); } /// /// Because Delete Events have a link to their corresponding Insert event, /// it is possible to compute exactly the range of events which must be /// compared to a given Insert event object. /// private void BuildIndex() { if (indexBuilt) return; events.Sort(); for (int i = 0; i < events.Count; i++) { SweepLineEvent ev = (SweepLineEvent)events[i]; if (ev.IsDelete) ev.InsertEvent.DeleteEventIndex = i; } indexBuilt = true; } /// /// /// /// public void ComputeOverlaps(ISweepLineOverlapAction action) { nOverlaps = 0; BuildIndex(); for (int i = 0; i < events.Count; i++) { SweepLineEvent ev = (SweepLineEvent)events[i]; if (ev.IsInsert) ProcessOverlaps(i, ev.DeleteEventIndex, ev.Interval, action); } } /// /// /// /// /// /// /// private void ProcessOverlaps(int start, int end, SweepLineInterval s0, ISweepLineOverlapAction action) { /* * Since we might need to test for self-intersections, * include current insert event object in list of event objects to test. * Last index can be skipped, because it must be a Delete event. */ for (int i = start; i < end; i++) { SweepLineEvent ev = (SweepLineEvent)events[i]; if (ev.IsInsert) { SweepLineInterval s1 = ev.Interval; action.Overlap(s0, s1); nOverlaps++; } } } } }