tiny-binary-search
Version:
Very small binary search index implimentation.
84 lines (66 loc) • 1.98 kB
JavaScript
function BinarySearchIndex (values) {
this.values = [].concat(values || []);
}
BinarySearchIndex.prototype.query = function (value) {
var index = this.getIndex(value);
return this.values[index];
};
BinarySearchIndex.prototype.getIndex = function getIndex (value) {
if (this.dirty) {
this.sort();
}
var minIndex = 0;
var maxIndex = this.values.length - 1;
var currentIndex;
var currentElement;
while (minIndex <= maxIndex) {
currentIndex = (minIndex + maxIndex) / 2 | 0;
currentElement = this.values[Math.round(currentIndex)];
if (+currentElement.value < +value) {
minIndex = currentIndex + 1;
} else if (+currentElement.value > +value) {
maxIndex = currentIndex - 1;
} else {
return currentIndex;
}
}
return Math.abs(~maxIndex);
};
BinarySearchIndex.prototype.between = function between (start, end) {
var startIndex = this.getIndex(start);
var endIndex = this.getIndex(end);
if (startIndex === 0 && endIndex === 0) {
return [];
}
while (this.values[startIndex - 1] && this.values[startIndex - 1].value === start) {
startIndex--;
}
while (this.values[endIndex + 1] && this.values[endIndex + 1].value === end) {
endIndex++;
}
if (this.values[endIndex] && this.values[endIndex].value === end && this.values[endIndex + 1]) {
endIndex++;
}
return this.values.slice(startIndex, endIndex);
};
BinarySearchIndex.prototype.insert = function insert (item) {
this.values.splice(this.getIndex(item.value), 0, item);
return this;
};
BinarySearchIndex.prototype.bulkAdd = function bulkAdd (items, sort) {
this.values = this.values.concat([].concat(items || []));
if (sort) {
this.sort();
} else {
this.dirty = true;
}
return this;
};
BinarySearchIndex.prototype.sort = function sort () {
this.values.sort(function (a, b) {
return +b.value - +a.value;
}).reverse();
this.dirty = false;
return this;
};
export default BinarySearchIndex;