大家好,欢迎来到无限大的频道。
今日继续给大家带来力扣题解。
题目描述(中等):
坐上公交的最晚时间
给你一个下标从 0 开始长度为 n 的整数数组 buses ,其中 buses[i] 表示第 i 辆公交车的出发时间。同时给你一个下标从 0 开始长度为 m 的整数数组 passengers ,其中 passengers[j] 表示第 j 位乘客的到达时间。所有公交车出发的时间互不相同,所有乘客到达的时间也互不相同。
给你一个整数 capacity ,表示每辆公交车 最多 能容纳的乘客数目。
每位乘客都会搭乘下一辆有座位的公交车。如果你在 y 时刻到达,公交在 x 时刻出发,满足 y <= x 且公交没有满,那么你可以搭乘这一辆公交。最早 到达的乘客优先上车。
返回你可以搭乘公交车的最晚到达公交站时间。你 不能 跟别的乘客同时刻到达。
注意:数组 buses 和 passengers 不一定是有序的。
解题思路:
-
排序:
-
首先,对 buses 和 passengers 数组进行排序。这样可以确保我们按照时间顺序处理公交车和乘客。
-
-
模拟乘客上车:
-
对于每辆公交车,初始化 space 为 capacity。
-
使用一个 while 循环,让乘客按顺序上车,直到公交车坐满或者没有乘客能在此时刻之前到达。
-
每次乘客上车后,减少 space,并增加 pos。
-
使用两个变量:pos 跟踪当前处理的乘客,space 表示当前公交车上剩余的座位数。
-
遍历每一辆公交车:
-
-
计算最晚到达时间:
-
在所有公交车处理完后,pos 指向最后一个已经上车的乘客的下一个位置。
-
如果最后一辆公交车还有空位(space > 0),则你可以在最后一辆公交车的出发时间到达。
-
如果没有空位,则你需要在最后一个乘客到达之前到达,因此 lastCatchTime 初始为 passengers[pos - 1]。
-
-
调整到达时间:
-
确保 lastCatchTime 不与任何乘客的到达时间相同,通过减少 lastCatchTime,直到它与任何乘客的到达时间不冲突。
-
代码参考:
int compare(const void *a, const void *b) {
return (*(int*)a - *(int*)b);
}
int latestTimeCatchTheBus(int* buses, int busesSize, int* passengers, int passengersSize, int capacity) {
qsort(buses, busesSize, sizeof(int), compare);
qsort(passengers, passengersSize, sizeof(int), compare);
int pos = 0;
int space = 0;
for (int i = 0; i < busesSize; i++) {
int arrive = buses[i];
space = capacity;
while (space > 0 && pos < passengersSize && passengers[pos] <= arrive) {
space--;
pos++;
}
}
pos--;
int lastCatchTime = space > 0 ? buses[busesSize - 1] : passengers[pos];
while (pos >= 0 && passengers[pos] == lastCatchTime) {
pos--;
lastCatchTime--;
}
return lastCatchTime;
}
时间复杂度:
-
排序:排序 buses 和 passengers 的时间复杂度分别是 O(n log n) 和 O(m log m),其中 n 是公交车数量,m 是乘客数量。
-
乘客上车模拟:遍历每辆公交车和每个乘客的过程是 O(n + m)。
-
调整到达时间:在最坏情况下,可能需要遍历所有乘客来调整 lastCatchTime,这个过程是 O(m)。
因此,总的时间复杂度为 O(n log n + m log m),因为排序操作是最耗时的部分。
空间复杂度:
-
代码中没有使用额外的数组或复杂的数据结构,除了输入数组和一些常数空间的变量之外,没有额外的空间开销。
-
因此,空间复杂度为 O(1)。