in processing/src/main/java/org/apache/druid/extendedset/intset/ConciseSet.java [1257:1378]
public int compareTo(IntSet o)
{
// empty set cases
if (this.isEmpty() && o.isEmpty()) {
return 0;
}
if (this.isEmpty()) {
return -1;
}
if (o.isEmpty()) {
return 1;
}
final ConciseSet other = convert(o);
// the word at the end must be the same
int res = Integer.compare(this.last, other.last);
if (res != 0) {
return res;
}
// scan words from MSB to LSB
int thisIndex = this.lastWordIndex;
int otherIndex = other.lastWordIndex;
int thisWord = this.words[thisIndex];
int otherWord = other.words[otherIndex];
while (thisIndex >= 0 && otherIndex >= 0) {
if (!isLiteral(thisWord)) {
if (!isLiteral(otherWord)) {
// compare two sequences
// note that they are made up of at least two blocks, and we
// start comparing from the end, that is at blocks with no
// (un)set bits
if (isZeroSequence(thisWord)) {
if (isOneSequence(otherWord)) {
// zeros < ones
return -1;
}
// compare two sequences of zeros
res = Integer.compare(getSequenceCount(otherWord), getSequenceCount(thisWord));
if (res != 0) {
return res;
}
} else {
if (isZeroSequence(otherWord)) {
// ones > zeros
return 1;
}
// compare two sequences of ones
res = Integer.compare(getSequenceCount(thisWord), getSequenceCount(otherWord));
if (res != 0) {
return res;
}
}
// if the sequences are the same (both zeros or both ones)
// and have the same length, compare the first blocks in the
// next loop since such blocks might contain (un)set bits
thisWord = getLiteral(thisWord);
otherWord = getLiteral(otherWord);
} else {
// zeros < literal --> -1
// ones > literal --> +1
// note that the sequence is made up of at least two blocks,
// and we start comparing from the end, that is at a block
// with no (un)set bits
if (isZeroSequence(thisWord)) {
if (otherWord != ConciseSetUtils.ALL_ZEROS_LITERAL) {
return -1;
}
} else {
if (otherWord != ConciseSetUtils.ALL_ONES_LITERAL) {
return 1;
}
}
if (getSequenceCount(thisWord) == 1) {
thisWord = getLiteral(thisWord);
} else {
thisWord--;
}
if (--otherIndex >= 0) {
otherWord = other.words[otherIndex];
}
}
} else if (!isLiteral(otherWord)) {
// literal > zeros --> +1
// literal < ones --> -1
// note that the sequence is made up of at least two blocks,
// and we start comparing from the end, that is at a block
// with no (un)set bits
if (isZeroSequence(otherWord)) {
if (thisWord != ConciseSetUtils.ALL_ZEROS_LITERAL) {
return 1;
}
} else {
if (thisWord != ConciseSetUtils.ALL_ONES_LITERAL) {
return -1;
}
}
if (--thisIndex >= 0) {
thisWord = this.words[thisIndex];
}
if (getSequenceCount(otherWord) == 1) {
otherWord = getLiteral(otherWord);
} else {
otherWord--;
}
} else {
// equals compare(getLiteralBits(thisWord), getLiteralBits(otherWord))
res = Integer.compare(thisWord, otherWord);
if (res != 0) {
return res;
}
if (--thisIndex >= 0) {
thisWord = this.words[thisIndex];
}
if (--otherIndex >= 0) {
otherWord = other.words[otherIndex];
}
}
}
return thisIndex >= 0 ? 1 : (otherIndex >= 0 ? -1 : 0);
}