def _is_overlap(i, j, used_spans):
    """
    Returns whether the span (i, j) overlaps with the interval(s) described by the items in `used_spans`
    """
    minval = min([i] + [s[0] for s in used_spans])  # smallest start index among spans
    maxval = max([j] + [s[1] for s in used_spans])  # largest end index among spans
    used_words = [0]*(maxval - minval + 1)
    for (span_start, span_end) in used_spans:
        assert used_words[span_start-minval: span_end-minval+1] == [0]*(span_end-span_start+1)  # check that no span has covered these words, which should be the case because spans aren't allowed to overlap
        used_words[span_start-minval: span_end-minval+1] = [1]*(span_end-span_start+1)  # (inclusive) interval has now been covered by a span

    return sum(used_words[i-minval: j-minval+1]) > 0