Welcome to Subscribe On Youtube
2080. Range Frequency Queries
Description
Design a data structure to find the frequency of a given value in a given subarray.
The frequency of a value in a subarray is the number of occurrences of that value in the subarray.
Implement the RangeFreqQuery
class:
RangeFreqQuery(int[] arr)
Constructs an instance of the class with the given 0-indexed integer arrayarr
.int query(int left, int right, int value)
Returns the frequency ofvalue
in the subarrayarr[left...right]
.
A subarray is a contiguous sequence of elements within an array. arr[left...right]
denotes the subarray that contains the elements of nums
between indices left
and right
(inclusive).
Example 1:
Input ["RangeFreqQuery", "query", "query"] [[[12, 33, 4, 56, 22, 2, 34, 33, 22, 12, 34, 56]], [1, 2, 4], [0, 11, 33]] Output [null, 1, 2] Explanation RangeFreqQuery rangeFreqQuery = new RangeFreqQuery([12, 33, 4, 56, 22, 2, 34, 33, 22, 12, 34, 56]); rangeFreqQuery.query(1, 2, 4); // return 1. The value 4 occurs 1 time in the subarray [33, 4] rangeFreqQuery.query(0, 11, 33); // return 2. The value 33 occurs 2 times in the whole array.
Constraints:
1 <= arr.length <= 105
1 <= arr[i], value <= 104
0 <= left <= right < arr.length
- At most
105
calls will be made toquery
Solutions
-
class RangeFreqQuery { private Map<Integer, List<Integer>> mp = new HashMap<>(); public RangeFreqQuery(int[] arr) { for (int i = 0; i < arr.length; ++i) { mp.computeIfAbsent(arr[i], k -> new ArrayList<>()).add(i); } } public int query(int left, int right, int value) { if (!mp.containsKey(value)) { return 0; } List<Integer> arr = mp.get(value); int l = search(arr, left - 1); int r = search(arr, right); return r - l; } private int search(List<Integer> arr, int val) { int left = 0, right = arr.size(); while (left < right) { int mid = (left + right) >> 1; if (arr.get(mid) > val) { right = mid; } else { left = mid + 1; } } return left; } } /** * Your RangeFreqQuery object will be instantiated and called as such: * RangeFreqQuery obj = new RangeFreqQuery(arr); * int param_1 = obj.query(left,right,value); */
-
class RangeFreqQuery { public: unordered_map<int, vector<int>> mp; RangeFreqQuery(vector<int>& arr) { for (int i = 0; i < arr.size(); ++i) mp[arr[i]].push_back(i); } int query(int left, int right, int value) { if (!mp.count(value)) return 0; auto& arr = mp[value]; auto l = upper_bound(arr.begin(), arr.end(), left - 1); auto r = upper_bound(arr.begin(), arr.end(), right); return r - l; } }; /** * Your RangeFreqQuery object will be instantiated and called as such: * RangeFreqQuery* obj = new RangeFreqQuery(arr); * int param_1 = obj->query(left,right,value); */
-
class RangeFreqQuery: def __init__(self, arr: List[int]): self.mp = defaultdict(list) for i, x in enumerate(arr): self.mp[x].append(i) def query(self, left: int, right: int, value: int) -> int: if value not in self.mp: return 0 arr = self.mp[value] l, r = bisect_right(arr, left - 1), bisect_right(arr, right) return r - l # Your RangeFreqQuery object will be instantiated and called as such: # obj = RangeFreqQuery(arr) # param_1 = obj.query(left,right,value)
-
type RangeFreqQuery struct { mp map[int][]int } func Constructor(arr []int) RangeFreqQuery { mp := make(map[int][]int) for i, v := range arr { mp[v] = append(mp[v], i) } return RangeFreqQuery{mp} } func (this *RangeFreqQuery) Query(left int, right int, value int) int { arr := this.mp[value] l := sort.SearchInts(arr, left) r := sort.SearchInts(arr, right+1) return r - l } /** * Your RangeFreqQuery object will be instantiated and called as such: * obj := Constructor(arr); * param_1 := obj.Query(left,right,value); */
-
class RangeFreqQuery { private g: Map<number, number[]> = new Map(); constructor(arr: number[]) { for (let i = 0; i < arr.length; ++i) { if (!this.g.has(arr[i])) { this.g.set(arr[i], []); } this.g.get(arr[i])!.push(i); } } query(left: number, right: number, value: number): number { const idx = this.g.get(value); if (!idx) { return 0; } const search = (x: number): number => { let [l, r] = [0, idx.length]; while (l < r) { const mid = (l + r) >> 1; if (idx[mid] >= x) { r = mid; } else { l = mid + 1; } } return l; }; const l = search(left); const r = search(right + 1); return r - l; } } /** * Your RangeFreqQuery object will be instantiated and called as such: * var obj = new RangeFreqQuery(arr) * var param_1 = obj.query(left,right,value) */