• Codeforces Round #608 (Div. 2) D Portals


    #include<bits/stdc++.h>
    using namespace std;
    const int N=5010;
    int n,m,k;
    int a[N],b[N],c[N];//攻破所需人数,获得人数,奖励得分
    int l[N],d[N],f[N],h[N];//可以扔掉兵攻占i的最晚的点,累加到i的上限兵人数,这个点可以扔掉的兵数
    int idx[N];
    int ans;
    //看看这题有没有解,顺便求个前缀和:d[i]=b[1]+...+b[n]
    bool check() {
        int p=k;
        for(int i=1; i<=n; i++) {
            if(p<a[i]) return 1;
            p+=b[i],d[i]=p;//d[i]累加到i点为止的上限兵人数
        }
        return 0;
    }
    
    bool cmp(int a,int b) {//按照分数的大小 排序
        return c[a]>c[b];
    }
    //判断这个点能不能扔兵
    bool check2(int x) {
        for(int i=n; i>=x; i--) {
            if(h[i]==0) return 0;//如果后面有个点开始不能扔兵的话这个点也不能扔兵
        }
        return 1;
    }
    int main() {
        scanf("%d%d%d",&n,&m,&k);
        for(int i=1; i<=n; i++) {
            scanf("%d%d%d",&a[i],&b[i],&c[i]);
            l[i]=i,idx[i]=i;//初始化idx,以及扔兵位置
        }
        //读入每个portal最晚在哪里留下防守的
        for(int i=1; i<=m; i++) {
            int x,y;
            scanf("%d%d",&x,&y);
            l[y]=max(l[y],x);
        }
        //判断题目是否有解
        if(check()) {
            puts("-1");
            return 0;
        }
        //计算到这个点可以扔的兵数
        a[n+1]=0;
        for(int i=1; i<=n; i++) {
            h[i]=d[i]-a[i+1];
        }
        
        //将idx按照分数的大小排序
        sort(idx+1,idx+1+n,cmp);//把攻占分数从大到小排序
        
        for(int i=1; i<=n; i++) {
            //先取出分数最大的
            int x=idx[i];
            if(check2(l[x])) {
                //先判断这个点能不能留下士兵,因为要确保后面的城堡都能攻下来
                //如果能的话,那么后面的城堡的h都要减一
                for(int j=l[x]; j<=n; j++) h[j]--;
                ans+=c[x];
            }
        }
        printf("%d
    ",ans);
        return 0;
    }
  • 相关阅读:
    基于linux、c的倒排索引
    关于A类,B类,C类IP地址的网段和主机数的计算方法
    如何找出字典中的兄弟单词
    简单验证码识别程序(源码)
    (一)SVM的八股简介
    验证码识别程序
    倒排索引
    验证码识别技术 Captcha Decode Technology
    字符串的组合
    C# 中panel的mousewheel事件触发 (转)
  • 原文地址:https://www.cnblogs.com/QingyuYYYYY/p/12068825.html
Copyright © 2020-2023  润新知