Leetcode打卡:最近的房间

执行结果:通过

题目:1847 最近的房间

一个酒店里有 n 个房间,这些房间用二维整数数组 rooms 表示,其中 rooms[i] = [roomIdi, sizei] 表示有一个房间号为 roomIdi 的房间且它的面积为 sizei 。每一个房间号 roomIdi 保证是 独一无二 的。

同时给你 k 个查询,用二维数组 queries 表示,其中 queries[j] = [preferredj, minSizej] 。第 j 个查询的答案是满足如下条件的房间 id

  • 房间的面积 至少minSizej ,且
  • abs(id - preferredj) 的值 最小 ,其中 abs(x)x 的绝对值。

如果差的绝对值有 相等 的,选择 最小id 。如果 没有满足条件的房间 ,答案为 -1

请你返回长度为 k 的数组 answer ,其中answer[j] 为第 j 个查询的结果。

示例 1:

复制代码
输入:rooms = [[2,2],[1,2],[3,2]], queries = [[3,1],[3,3],[5,2]]
输出:[3,-1,3]
解释:查询的答案如下:
查询 [3,1] :房间 3 的面积为 2 ,大于等于 1 ,且号码是最接近 3 的,为 abs(3 - 3) = 0 ,所以答案为 3 。
查询 [3,3] :没有房间的面积至少为 3 ,所以答案为 -1 。
查询 [5,2] :房间 3 的面积为 2 ,大于等于 2 ,且号码是最接近 5 的,为 abs(3 - 5) = 2 ,所以答案为 3 。

示例 2:

复制代码
输入:rooms = [[1,4],[2,3],[3,5],[4,1],[5,2]], queries = [[2,3],[2,4],[2,5]]
输出:[2,1,3]
解释:查询的答案如下:
查询 [2,3] :房间 2 的面积为 3 ,大于等于 3 ,且号码是最接近的,为 abs(2 - 2) = 0 ,所以答案为 2 。
查询 [2,4] :房间 1 和 3 的面积都至少为 4 ,答案为 1 因为它房间编号更小。
查询 [2,5] :房间 3 是唯一面积大于等于 5 的,所以答案为 3 

提示:

  • n == rooms.length
  • 1 <= n <= 105
  • k == queries.length
  • 1 <= k <= 104
  • 1 <= roomIdi, preferredj <= 107
  • 1 <= sizei, minSizej <= 107

代码以及解题思路

代码:

/**
 * Note: The returned array must be malloced, assume caller calls free().
 */
 int cmp(const void *a, const void *b) {
    int *m = *(int **)a, *n = *(int **)b;
    if (m[1] != n[1]) {
        return m[1] - n[1];
    }
    else {
        return m[0] - n[0];
    }
}

int* closestRoom(int** rooms, int roomsSize, int* roomsColSize, int** queries, int queriesSize, int* queriesColSize, int* returnSize) {
    int *res = (int *)malloc(sizeof(int) * queriesSize);
   *returnSize = queriesSize;
    qsort(rooms, roomsSize, sizeof(int *), cmp);
    
    int left, right;

    for (int i = 0; i < queriesSize; i++) {
        if (i > 0) { //这个地方优化最后2个测试用例,否则超时
            if (queries[i][1] == queries[i - 1][1] && queries[i][0] == queries[i - 1][0]) {
                res[i] = res[i - 1];
                continue;
            }
        }
        left = 0;
        right = roomsSize - 1;
        while (left <= right) {
            int mid = left + (right - left) / 2;
            if (rooms[mid][1] >= queries[i][1]) {
                right = mid - 1;
            } else {
                left = mid + 1;
            }
        }

        if (right == roomsSize - 1) {
            res[i] = -1;
            continue;
        }

        left = right + 1;
        right = roomsSize - 1;
        int absVal = abs(queries[i][0] - rooms[left][0]);
        res[i] = rooms[left][0];
        for (int j = left + 1; j <= right; j++) {
            int temp = abs(queries[i][0] - rooms[j][0]);
            if (temp < absVal) {
                absVal = temp;
                res[i] = rooms[j][0];
            } else if (temp == absVal) {
                if (rooms[j][0] < res[i]) {
                    res[i] = rooms[j][0];
                }
            }
        }
    }

    return res; 

}

解题思路:

  1. 内存分配
    • 为结果数组 res 分配内存,其大小为 queriesSize,因为对于每个查询都需要一个结果。
    • 通过 *returnSize = queriesSize; 设置返回数组的大小。
  2. 排序
    • 使用 qsort 函数对 rooms 数组进行排序。排序的依据是房间的 y 坐标,如果 y 坐标相同,则按 x 坐标排序。这是为了确保在后续的二分查找中,我们可以快速定位到与查询 y 坐标最接近的房间。
  3. 遍历查询
    • 对于每个查询,首先检查是否与前一个查询相同(这是为了优化性能,避免对相同的查询进行重复计算)。如果相同,则直接使用前一个查询的结果。
    • 使用二分查找定位到 rooms 数组中第一个 y 坐标大于查询 y 坐标的房间的左侧位置(即该位置房间的 y 坐标小于或等于查询的 y 坐标,而下一个位置的 y 坐标大于查询的 y 坐标,或者该位置已经是数组的最后一个元素)。
  4. 处理边界情况
    • 如果二分查找的结果指向数组的最后一个元素,并且该元素的 y 坐标仍然小于查询的 y 坐标,则说明没有找到任何符合条件的房间,将结果设置为 -1。
  5. 在二分查找结果的基础上寻找最接近的房间
    • 从二分查找确定的左侧位置的下一个位置开始,遍历剩余的房间,找到与查询 x 坐标最接近的房间的 x 坐标。如果有多个房间与查询的 x 坐标距离相同,则选择 x 坐标最小的那个。
  6. 返回结果
    • 返回结果数组 res,其中包含了每个查询对应的最接近房间的 x 坐标或 -1(如果没有找到任何房间)。
相关推荐
Solitudefire21 分钟前
蓝桥杯刷题——day6
职场和发展·蓝桥杯
一行玩python25 分钟前
PugiXML,一个高效且简单的 C++ XML 解析库!
xml·开发语言·c++·算法
Sunyanhui11 小时前
牛客网 SQL1查询所有列
c++·算法
所有向日癸上升1 小时前
问题 C: B001 快乐的蠕虫
c语言·开发语言·算法
Cooloooo2 小时前
二叉搜索树Ⅲ【东北大学oj数据结构8-3】C++
数据结构·c++·算法
互联网杂货铺2 小时前
单元测试总结
自动化测试·软件测试·python·测试工具·职场和发展·单元测试·测试用例
sjsjs113 小时前
【多维DP】力扣2370. 最长理想子序列
算法·leetcode·动态规划
在西湖雾雨中起舞3 小时前
题目 2834: 与指定数字相同的数的个数
数据结构·c++·算法
抓个马尾女孩4 小时前
Python中列表复制A=B和A=B[:]的区别
数据结构·python·算法
陌繁4 小时前
LeetCode1.两数之和(超简单讲解)
数据结构·算法·leetcode