Back to all solutions
#2276 - Count Integers in Intervals
Problem Description
Given an empty set of intervals, implement a data structure that can:
- Add an interval to the set of intervals.
- Count the number of integers that are present in at least one interval.
Implement the CountIntervals class:
- CountIntervals() Initializes the object with an empty set of intervals.
- void add(int left, int right) Adds the interval [left, right] to the set of intervals.
- int count() Returns the number of integers that are present in at least one interval.
Note that an interval [left, right] denotes all the integers x where left <= x <= right.
Solution
var CountIntervals = function() {
this.coverage = 0;
this.intervals = [[-Infinity, -Infinity], [Infinity, Infinity]];
};
/**
* @param {number} left
* @param {number} right
* @return {void}
*/
CountIntervals.prototype.add = function(left, right) {
function bisectLeft(arr, target) {
let low = 0;
let high = arr.length;
while (low < high) {
const mid = Math.floor((low + high) / 2);
if (arr[mid][0] < target) {
low = mid + 1;
} else {
high = mid;
}
}
return low;
}
function bisectRight(arr, target) {
let low = 0;
let high = arr.length;
while (low < high) {
const mid = Math.floor((low + high) / 2);
if (arr[mid][0] <= target) {
low = mid + 1;
} else {
high = mid;
}
}
return low;
}
let li = bisectLeft(this.intervals, left - 1);
if (this.intervals[li - 1][1] >= left - 1) {
li -= 1;
}
const lval = Math.min(this.intervals[li][0], left);
const ri = bisectRight(this.intervals, right + 1);
const rval = Math.max(this.intervals[ri - 1][1], right);
let toDelete = 0;
for (let i = li; i < ri; i++) {
toDelete += this.intervals[i][1] - this.intervals[i][0] + 1;
}
this.coverage += rval - lval + 1 - toDelete;
this.intervals.splice(li, ri - li, [lval, rval]);
};
/**
* @return {number}
*/
CountIntervals.prototype.count = function() {
return this.coverage;
};