private static Set<Range> intersectionOneWrapping(Range wrapping, Range other) { Set<Range> intersection = new HashSet<Range>(2); if (other.contains(wrapping.right)) intersection.add(new Range(other.left, wrapping.right)); // need the extra compareto here because ranges are asymmetrical; wrapping.left _is not_ // contained by the wrapping range if (other.contains(wrapping.left) && wrapping.left.compareTo(other.right) < 0) intersection.add(new Range(wrapping.left, other.right)); return Collections.unmodifiableSet(intersection); }
public static boolean isTokenInRanges(Token token, Iterable<Range> ranges) { assert ranges != null; for (Range range : ranges) { if (range.contains(token)) { return true; } } return false; }
/** * @param that * @return the intersection of the two Ranges. this can be two disjoint Ranges if one is wrapping * and one is not. say you have nodes G and M, with query range (D,T]; the intersection is * (M-T] and (D-G]. If there is no intersection, an empty list is returned. */ public Set<Range> intersectionWith(Range that) { if (that.contains(this)) return rangeSet(this); if (this.contains(that)) return rangeSet(that); boolean thiswraps = isWrapAround(left, right); boolean thatwraps = isWrapAround(that.left, that.right); if (!thiswraps && !thatwraps) { // neither wraps. the straightforward case. if (!(left.compareTo(that.right) < 0 && that.left.compareTo(right) < 0)) return Collections.emptySet(); return rangeSet( new Range( (Token) ObjectUtils.max(this.left, that.left), (Token) ObjectUtils.min(this.right, that.right))); } if (thiswraps && thatwraps) { // if the starts are the same, one contains the other, which we have already ruled out. assert !this.left.equals(that.left); // two wrapping ranges always intersect. // since we have already determined that neither this nor that contains the other, we have 2 // cases, // and mirror images of those case. // (1) both of that's (1, 2] endpoints lie in this's (A, B] right segment: // ---------B--------A--1----2------> // (2) only that's start endpoint lies in this's right segment: // ---------B----1---A-------2------> // or, we have the same cases on the left segement, which we can handle by swapping this and // that. return this.left.compareTo(that.left) < 0 ? intersectionBothWrapping(this, that) : intersectionBothWrapping(that, this); } if (thiswraps && !thatwraps) return intersectionOneWrapping(this, that); assert (!thiswraps && thatwraps); return intersectionOneWrapping(that, this); }