思路
这题意思就是在一段滑动串口里,对于任意一个数x,是否存在一个数 y 使得 abs(x - y) <= t ,即大小最接近y的数是否能满足条件。
很明显使用 lower_bound()函数来求,lower_bound()可以实现在一段排序的数列中,对于x,可以找出第一个>=x的数所在的位置,而set容器支持lower_bound()操作,multiset则可以实现滑动的有序排列,且支持插入和删除的操作,解法就显而易见;
需要注意的是,题目给值范围如果用int会越界;lower_bound时设置两个端点处哨兵;以及在multiset中删除元素时,需要删除的是下标i处的迭代器,而不是下标i处在容器中对应的值。
代码
class Solution {
public:
bool containsNearbyAlmostDuplicate(vector<int>& nums, int k, int t) {
typedef long long LL;
multiset<LL>hash;
hash.insert(1e18), hash.insert(-1e18); // 进行lower_bound时需要使用的边界
for (int i = 0, j = 0; i < nums.size(); i++) {
if (i - j > k) hash.erase(hash.find(nums[j++])); // 要删除迭代器,不然可能删除重复元素,可能有多个迭代器的值为相同值,这里只是删去其中任意一个不影响最终结果。
LL x = nums[i];
auto it = hash.lower_bound(x);
if (abs (*it - x) <= t) return true;
--it; // 找到比 x 小的第一个数
if (abs (*it - x) <= t) return true;
hash.insert(x);
}
return false;
}
};