Skip to content

Commit 35ea85e

Browse files
committed
1 parent c8f3b0e commit 35ea85e

File tree

2 files changed

+156
-0
lines changed

2 files changed

+156
-0
lines changed

src/solution/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1724,3 +1724,4 @@ mod s2272_substring_with_largest_variance;
17241724
mod s2273_find_resultant_array_after_removing_anagrams;
17251725
mod s2274_maximum_consecutive_floors_without_special_floors;
17261726
mod s2275_largest_combination_with_bitwise_and_greater_than_zero;
1727+
mod s2276_count_integers_in_intervals;
Lines changed: 155 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,155 @@
1+
/**
2+
* [2276] Count Integers in Intervals
3+
*
4+
* Given an empty set of intervals, implement a data structure that can:
5+
*
6+
* Add an interval to the set of intervals.
7+
* Count the number of integers that are present in at least one interval.
8+
*
9+
* Implement the CountIntervals class:
10+
*
11+
* CountIntervals() Initializes the object with an empty set of intervals.
12+
* void add(int left, int right) Adds the interval [left, right] to the set of intervals.
13+
* int count() Returns the number of integers that are present in at least one interval.
14+
*
15+
* Note that an interval [left, right] denotes all the integers x where left <= x <= right.
16+
*
17+
* Example 1:
18+
*
19+
* Input
20+
* ["CountIntervals", "add", "add", "count", "add", "count"]
21+
* [[], [2, 3], [7, 10], [], [5, 8], []]
22+
* Output
23+
* [null, null, null, 6, null, 8]
24+
* Explanation
25+
* CountIntervals countIntervals = new CountIntervals(); // initialize the object with an empty set of intervals.
26+
* countIntervals.add(2, 3); // add [2, 3] to the set of intervals.
27+
* countIntervals.add(7, 10); // add [7, 10] to the set of intervals.
28+
* countIntervals.count(); // return 6
29+
* // the integers 2 and 3 are present in the interval [2, 3].
30+
* // the integers 7, 8, 9, and 10 are present in the interval [7, 10].
31+
* countIntervals.add(5, 8); // add [5, 8] to the set of intervals.
32+
* countIntervals.count(); // return 8
33+
* // the integers 2 and 3 are present in the interval [2, 3].
34+
* // the integers 5 and 6 are present in the interval [5, 8].
35+
* // the integers 7 and 8 are present in the intervals [5, 8] and [7, 10].
36+
* // the integers 9 and 10 are present in the interval [7, 10].
37+
*
38+
*
39+
* Constraints:
40+
*
41+
* 1 <= left <= right <= 10^9
42+
* At most 10^5 calls in total will be made to add and count.
43+
* At least one call will be made to count.
44+
*
45+
*/
46+
pub struct Solution {}
47+
48+
// problem: https://leetcode.com/problems/count-integers-in-intervals/
49+
// discuss: https://leetcode.com/problems/count-integers-in-intervals/discuss/?currentPage=1&orderBy=most_votes&query=
50+
51+
// submission codes start here
52+
53+
// Credit: https://leetcode.com/problems/count-integers-in-intervals/solutions/2375879/rust-solution-using-btreemap-by-xiaoping-pshe/
54+
55+
struct CountIntervals {
56+
count: i32,
57+
map: std::collections::BTreeMap<i32, i32>,
58+
}
59+
60+
/**
61+
* `&self` means the method takes an immutable reference.
62+
* If you need a mutable reference, change it to `&mut self` instead.
63+
*/
64+
impl CountIntervals {
65+
fn new() -> Self {
66+
let mp: std::collections::BTreeMap<i32, i32> = std::collections::BTreeMap::new();
67+
Self { count: 0, map: mp }
68+
}
69+
70+
fn add(&mut self, left: i32, right: i32) {
71+
let (mut left, mut right) = (left, right);
72+
73+
self.count += right - left + 1;
74+
if self.map.is_empty() {
75+
self.map.insert(left, right);
76+
return;
77+
}
78+
79+
let (a, _) = self.map.iter().next().unwrap();
80+
let (_, b) = self.map.iter().rev().next().unwrap();
81+
if a - 1 > right || b + 1 < left {
82+
self.map.insert(left, right);
83+
return;
84+
}
85+
86+
if let Some((&key, &value)) = self.map.range(..left + 1).rev().next() {
87+
if value + 1 >= left {
88+
if value > right {
89+
self.count -= right - left + 1;
90+
} else {
91+
self.count -= value + 1 - left;
92+
}
93+
left = key;
94+
right = right.max(value);
95+
}
96+
}
97+
98+
let mut done = false;
99+
while done == false {
100+
done = true;
101+
if let Some((&key, &value)) = self.map.range(left + 1..).next() {
102+
if value > right {
103+
break;
104+
}
105+
self.count -= value - key + 1;
106+
self.map.remove(&key);
107+
done = false;
108+
}
109+
}
110+
111+
if let Some((&key, &value)) = self.map.range(left + 1..).next() {
112+
if right + 1 >= key {
113+
self.count -= right + 1 - key;
114+
right = value;
115+
self.map.remove(&key);
116+
}
117+
}
118+
119+
self.map.insert(left, right);
120+
}
121+
122+
fn count(&self) -> i32 {
123+
self.count
124+
}
125+
}
126+
127+
/**
128+
* Your CountIntervals object will be instantiated and called as such:
129+
* let obj = CountIntervals::new();
130+
* obj.add(left, right);
131+
* let ret_2: i32 = obj.count();
132+
*/
133+
134+
// submission codes end
135+
136+
#[cfg(test)]
137+
mod tests {
138+
use super::*;
139+
140+
#[test]
141+
fn test_2276_example_1() {
142+
let mut count_intervals = CountIntervals::new(); // initialize the object with an empty set of intervals.
143+
count_intervals.add(2, 3); // add [2, 3] to the set of intervals.
144+
count_intervals.add(7, 10); // add [7, 10] to the set of intervals.
145+
assert_eq!(count_intervals.count(), 6); // return 6
146+
// the integers 2 and 3 are present in the interval [2, 3].
147+
// the integers 7, 8, 9, and 10 are present in the interval [7, 10].
148+
count_intervals.add(5, 8); // add [5, 8] to the set of intervals.
149+
assert_eq!(count_intervals.count(), 8); // return 8
150+
// the integers 2 and 3 are present in the interval [2, 3].
151+
// the integers 5 and 6 are present in the interval [5, 8].
152+
// the integers 7 and 8 are present in the intervals [5, 8] and [7, 10].
153+
// the integers 9 and 10 are present in the interval [7, 10].
154+
}
155+
}

0 commit comments

Comments
 (0)