其他分享
首页 > 其他分享> > LeetCode 1792. 最大平均通过率(堆)

LeetCode 1792. 最大平均通过率(堆)

作者:互联网

题意:

一所学校里有一些班级,每个班级里有一些学生,现在每个班都会进行一场期末考试。
给你一个二维数组 classes ,其中 classes[i] = [passi, totali] ,
表示你提前知道了第 i 个班级总共有 totali 个学生,其中只有 passi 个学生可以通过考试。

给你一个整数 extraStudents ,表示额外有 extraStudents 个聪明的学生,他们 一定 能通过任何班级的期末考。
你需要给这 extraStudents 个学生每人都安排一个班级,使得 所有 班级的 平均 通过率 最大 。

一个班级的 通过率 等于这个班级通过考试的学生人数除以这个班级的总人数。
平均通过率 是所有班级的通过率之和除以班级数目。

请你返回在安排这 extraStudents 个学生去对应班级后的 最大 平均通过率。
与标准答案误差范围在 1e-5 以内的结果都会视为正确结果。

数据范围:
1 <= classes.length <= 1e5
classes[i].length == 2
1 <= passi <= totali <= 1e5
1 <= extraStudents <= 1e5

解法:

因为班级数量是固定的,最大化平均通过率其实就是最大化总通过率.

对于(x,y),加一个学生之后变成(x+1,y+1),通过率的变化量为(x+1)/(y+1)-x/y.
用一个堆存所有二元组(x,y),每次贪心地取出变化量最大的出来即可.

原理是每次添加之后,下一次添加的变化量一定会比这次小,所以每次用堆选出变化量最大的.

code:

struct PI{
    int x,y;
    bool operator<(const PI &t)const{
        double a=(x+1)*1.0/(y+1)-x*1.0/y;
        double b=(t.x+1)*1.0/(t.y+1)-t.x*1.0/t.y;
        return a<b;
    }
};
class Solution {
public:
    double maxAverageRatio(vector<vector<int>>& e, int p) {
        priority_queue<PI>q;
        for(auto i:e){
            q.push({i[0],i[1]});
        }
        while(p--){
            PI x=q.top();q.pop();
            x.x++,x.y++;
            q.push(x);
        }
        double ans=0;
        while(q.size()){
            PI x=q.top();q.pop();
            ans+=(x.x)*1.0/x.y;
        }
        ans/=(int)e.size();
        return ans;
    }
};

标签:班级,1.0,1792,ans,extraStudents,double,LeetCode,通过率
来源: https://blog.csdn.net/weixin_44178736/article/details/114822122