public override void Overlap(MonotoneChain mc1, int start1, MonotoneChain mc2, int start2) { var ss1 = (ISegmentString)mc1.Context; var ss2 = (ISegmentString)mc2.Context; _si.ProcessIntersections(ss1, start1, ss2, start2); }
/// <summary> /// Return a list of the <c>MonotoneChain</c>s /// for the given list of coordinates. /// </summary> /// <param name="pts"></param> /// <param name="context"></param> public static IList<MonotoneChain> GetChains(Coordinate[] pts, object context) { var mcList = new List<MonotoneChain>(); var startIndex = GetChainStartIndices(pts); for (var i = 0; i < startIndex.Length - 1; i++) { var mc = new MonotoneChain(pts, startIndex[i], startIndex[i + 1], context); mcList.Add(mc); } return mcList; }
/// <summary> /// /// </summary> /// <param name="start0"></param> /// <param name="end0"></param> /// <param name="mc"></param> /// <param name="start1"></param> /// <param name="end1"></param> /// <param name="mco"></param> private void ComputeOverlaps(int start0, int end0, MonotoneChain mc, int start1, int end1, MonotoneChainOverlapAction mco) { Coordinate p00 = _pts[start0]; Coordinate p01 = _pts[end0]; Coordinate p10 = mc._pts[start1]; Coordinate p11 = mc._pts[end1]; // terminating condition for the recursion if (end0 - start0 == 1 && end1 - start1 == 1) { mco.Overlap(this, start0, mc, start1); return; } // nothing to do if the envelopes of these chains don't overlap mco.TempEnv1.Init(p00, p01); mco.TempEnv2.Init(p10, p11); if (! mco.TempEnv1.Intersects(mco.TempEnv2)) return; // the chains overlap, so split each in half and iterate (binary search) int mid0 = (start0 + end0) / 2; int mid1 = (start1 + end1) / 2; // Assert: mid != start or end (since we checked above for end - start <= 1) // check terminating conditions before recursing if (start0 < mid0) { if (start1 < mid1) ComputeOverlaps(start0, mid0, mc, start1, mid1, mco); if (mid1 < end1) ComputeOverlaps(start0, mid0, mc, mid1, end1, mco); } if (mid0 < end0) { if (start1 < mid1) ComputeOverlaps(mid0, end0, mc, start1, mid1, mco); if (mid1 < end1) ComputeOverlaps(mid0, end0, mc, mid1, end1, mco); } }
/** * * <p> * * @param searchEnv the search envelope * @param mco t */ /// <summary> /// Determine all the line segments in two chains which may overlap, and process them. /// </summary> /// <remarks> /// The monotone chain search algorithm attempts to optimize /// performance by not calling the overlap action on chain segments /// which it can determine do not overlap. /// However, it *may* call the overlap action on segments /// which do not actually interact. /// This saves on the overhead of checking intersection /// each time, since clients may be able to do this more efficiently. /// </remarks> /// <param name="mc">The monotone chain</param> /// <param name="mco">The overlap action to execute on selected segments</param> public void ComputeOverlaps(MonotoneChain mc, MonotoneChainOverlapAction mco) { ComputeOverlaps(_start, _end, mc, mc._start, mc._end, mco); }
/// <summary> /// This function can be overridden if the original chains are needed. /// </summary> /// <param name="mc1"></param> /// <param name="start1">The index of the start of the overlapping segment from mc1.</param> /// <param name="mc2"></param> /// <param name="start2">The index of the start of the overlapping segment from mc2.</param> public virtual void Overlap(MonotoneChain mc1, int start1, MonotoneChain mc2, int start2) { mc1.GetLineSegment(start1, ref overlapSeg1); mc2.GetLineSegment(start2, ref overlapSeg2); Overlap(overlapSeg1, overlapSeg2); }
/// <summary> /// /// </summary> /// <param name="rayEnv"></param> /// <param name="mcSelecter"></param> /// <param name="mc"></param> private static void TestMonotoneChain(Envelope rayEnv, MCSelecter mcSelecter, MonotoneChain mc) { mc.Select(rayEnv, mcSelecter); }
/// <summary> /// /// </summary> /// <param name="mc1"></param> /// <param name="start1"></param> /// <param name="mc2"></param> /// <param name="start2"></param> public override void Overlap(MonotoneChain mc1, int start1, MonotoneChain mc2, int start2) { var ss1 = (ISegmentString) mc1.Context; var ss2 = (ISegmentString) mc2.Context; _si.ProcessIntersections(ss1, start1, ss2, start2); }
/// <summary> /// This method is overridden to process a segment /// in the context of the parent chain. /// </summary> /// <param name="mc">The parent chain</param> /// <param name="startIndex">The index of the start vertex of the segment being processed</param> public virtual void Select(MonotoneChain mc, int startIndex) { mc.GetLineSegment(startIndex, ref SelectedSegment); // call this routine in case select(segment) was overridden Select(SelectedSegment); }
/// <summary> /// Determine all the line segments in two chains which may overlap, and process them. /// </summary> /// <remarks> /// The monotone chain search algorithm attempts to optimize /// performance by not calling the overlap action on chain segments /// which it can determine do not overlap. /// However, it *may* call the overlap action on segments /// which do not actually interact. /// This saves on the overhead of checking intersection /// each time, since clients may be able to do this more efficiently. /// </remarks> /// <param name="mc">The monotone chain</param> /// <param name="mco">The overlap action to execute on selected segments</param> public void ComputeOverlaps(MonotoneChain mc, MonotoneChainOverlapAction mco) { ComputeOverlaps(_start, _end, mc, mc._start, mc._end, mco); }
/// <summary> /// This method is overridden to process a segment /// in the context of the parent chain. /// </summary> /// <param name="mc">The parent chain</param> /// <param name="startIndex">The index of the start vertex of the segment being processed</param> public virtual void Select(MonotoneChain mc, int startIndex) { mc.GetLineSegment(startIndex, ref SelectedSegment); // call this routine in case select(segmenet) was overridden Select(SelectedSegment); }