#3488
Medium Algorithms Closest equal element queries
Array Hash Table Binary Search
32.8% acceptance
Feb 25, 2026
120
10
You are given a circular array nums and an array queries.
For each query i, you have to find the following:
The minimum distance between the element at index queries[i] and any other index j in the circular array, where nums[j] == nums[queries[i]]. If no such index exists, the answer for that query should be -1.
Return an array answer of the same size as queries, where answer[i] represents the result for query i.
Solution
Rust
Time O(n log n)
Space O(n)
impl Solution {
pub fn solve_queries(nums: Vec<i32>, queries: Vec<i32>) -> Vec<i32> {
use std::collections::HashMap;
let n = nums.len();
let mut positions: HashMap<i32, Vec<usize>> = HashMap::new();
for (i, &v) in nums.iter().enumerate() {
positions.entry(v).or_default().push(i);
}
queries.iter().map(|&q| {
let q = q as usize;
let v = nums[q];
let pos = positions.get(&v).unwrap();
if pos.len() < 2 { return -1; }
// Find min circular distance from q to any other pos
let idx = pos.partition_point(|&p| p < q);
let mut min_dist = i32::MAX;
// prev occurrence
if idx > 0 {
let d = q - pos[idx-1];
min_dist = min_dist.min(d.min(n - d) as i32);
}
// next occurrence
if idx < pos.len() - 1 || (idx > 0 && pos[idx] == q) {
let next_idx = if pos[idx] == q { idx + 1 } else { idx };
if next_idx < pos.len() {
let d = pos[next_idx] - q;
min_dist = min_dist.min(d.min(n - d) as i32);
}
}
// wrap around: first and last in circular
if pos.len() >= 2 {
let first = pos[0]; let last = *pos.last().unwrap();
if first != q {
let d = if q > first { q - first } else { first - q };
min_dist = min_dist.min(d.min(n - d) as i32);
}
if last != q {
let d = if q > last { q - last } else { last - q };
min_dist = min_dist.min(d.min(n - d) as i32);
}
}
if min_dist == i32::MAX { -1 } else { min_dist }
}).collect()
}
}