这里有 n 门不同的在线课程,按从 1 到 n 编号。给你一个数组 courses ,其中 courses[i] = [durationi, lastDayi] 表示第 i 门课将会 持续 上 durationi 天课,并且必须在不晚于 lastDayi 的时候完成。
你的学期从第 1 天开始。且不能同时修读两门及两门以上的课程。
返回你最多可以修读的课程数目。
示例 1:
输入:courses = [[100, 200], [200, 1300], [1000, 1250], [2000, 3200]]
输出:3
解释:
这里一共有 4 门课程,但是你最多可以修 3 门:
首先,修第 1 门课,耗费 100 天,在第 100 天完成,在第 101 天开始下门课。
第二,修第 3 门课,耗费 1000 天,在第 1100 天完成,在第 1101 天开始下门课程。
第三,修第 2 门课,耗时 200 天,在第 1300 天完成。
第 4 门课现在不能修,因为将会在第 3300 天完成它,这已经超出了关闭日期。
示例 2:
输入:courses = [[1,2]]
输出:1
示例 3:
输入:courses = [[3,2],[4,3]]
输出:0
提示:
1 <= courses.length <= 104
1 <= durationi, lastDayi <= 104
思路:为了上尽可能多的课程,我们应该优先考虑那些结课时间短的课程,因此可以首先将所有课程按照结课时间来从小到大排序。依次遍历每个课程,并累计当前的总计上课时间。
若当前课程无法在其截止日期前上完,则要么不上该门课,要么就在已经上的课程里去除一个比当前课程用时还多的课后,再来上这门课,贪心的想,也就是去掉一个当前上过的课中最费时的课程即可。
class Solution {
public:
int scheduleCourse(vector<vector<int>>& courses) {
sort(courses.begin(),courses.end(),[](vector<int> &a, vector<int> &b){
return a[1] < b[1];
});
priority_queue<int> q;
int now = 0;// 当前的总计上课时间
for(auto &v : courses){
now += v[0];// 直接上该门课
q.push(v[0]);
if(now > v[1]){//但门课无法在截止日期前上完 则去掉一个最费时的课程
now -= q.top();
q.pop();
}
}
return q.size();
}
};