码迷,mamicode.com
首页 > 其他好文 > 详细

cf 1020 round 503(SIS div2) C. Elections

时间:2019-01-13 21:40:58      阅读:177      评论:0      收藏:0      [点我收藏+]

标签:比赛   print   pac   获得   +=   数组   class   bool   bsp   

题意:给出n个人投票,开始每个人都有一个选好的人,如果我们要使它换票就必须支付他所给的价格,我们要使1号选手赢得比赛,问我们支付最少的钱是多少来使一号赢得胜利

思路: 我们考虑到纯贪心有太多种情况,题目所给的数据也是3000,说明我们可以使用n^2以至更高的算法,我们考虑1号选手获胜的状态,就是他是以几票来获得胜利的

枚举获胜状态,然后我们取最优的

给一个例子    1:0票        2:3票          3:3票       4:2票         5 :1票

1号选手1票获取胜利   不存在

2票获取胜利     不存在

3票获取胜利     如果我们要三票赢2号和3号,必须要比2号3号多一票才可以,但是我们总共只买三票,既然我们不能增多自己,只能削弱对手,

其中一票在2号这里买,那么他就会降为2票,3号同理,然后剩下一票,买价格最低的即可

然后四票五票获取胜利的方法同理,我们只要取花费价格最少的状态即可

#include<bits/stdc++.h>
using namespace std;
struct person{
    int p,c;
}per[3010];
int f[3010];
int g[3010];
bool cmp(person A,person B)
{
    return A.c<B.c;
}
int main()
{
    int n,m;
    scanf("%d%d",&n,&m);
    for(int i=1;i<=n;i++)
    {
        scanf("%d%d",&per[i].p,&per[i].c);
        f[per[i].p]++;
    }
    long long res=3e12;
    sort(per+1,per+n+1,cmp);
    for(int i=f[1];i<=n;i++)
    {
        int sum=0;
        for(int j=2;j<=m;j++)
        {
            if(f[j]>=i)
            {
                g[j]=f[j]-i+1;
                sum+=g[j];
            }
            else g[j]=0;//此处不可省略, g数组要反复更新 
        }
        if(i-f[1]<sum) continue;
        long long ans=0;
        sum=i-f[1]-sum;
        for(int j=1;j<=n;j++)
        {
            if(g[per[j].p]>0)
            {
                g[per[j].p]--;
                ans+=per[j].c;
            }
            else if(sum>0&&per[j].p!=1)
            {
                sum--;
                ans+=per[j].c;
            }
        }
        res=min(ans,res);
    }
    printf("%lld\n",res);
}

 

cf 1020 round 503(SIS div2) C. Elections

标签:比赛   print   pac   获得   +=   数组   class   bool   bsp   

原文地址:https://www.cnblogs.com/lishengkangshidatiancai/p/10264066.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!