0
点赞
收藏
分享

微信扫一扫

【贪心与实数运算】付账问题

sin信仰 2022-02-05 阅读 39

题目

 

解释

  • 要使得标准差最小,即每个人付的钱尽量保持在一个平均值
  • 当第i个人有的钱小于平均值时
  • 剩余的人为其垫付,因此重新计算平均值,以此贪心来求得全局得最稳定
  • 注意到求标准差时得平均值即总价格/人数,一直使用s/n的值减小误差

代码段

#include<cstdio>
#include<algorithm>
#include<cmath>
const int N=5*1e5+10;
using namespace std;
int n,s;
int a[N],b[N];
int main()
{
    scanf("%d%d",&n,&s);
    for(int i=1;i<=n;i++)
    scanf("%d",&a[i]);
    sort(a+1,a+n+1);
    double ave=s*1.0/n;
    double sum=0;
    double cur_ave=ave;
    for(int i=1;i<=n;i++)
    {
        if(a[i]<cur_ave)
        {
            s-=a[i];
            b[i]=a[i];
            sum+=(a[i]-ave)*(a[i]-ave);
            cur_ave=s*1.0/(n-i);
        }
        else
        {
        s-=cur_ave;
        b[i]=cur_ave;
        sum+=(ave-cur_ave)*(ave-cur_ave);
        }
    }
    printf("%.4lf",sqrt(sum/n));
}
举报

相关推荐

0 条评论