Codeforces Round #377 (Div. 2)

题目链接:https://codeforces.com/contest/732

A - Buy a Shovel

题意:有无穷枚10元硬币和1枚r元硬币,且r是[1,9]。每个物品的单价是x元,求最少买多少件不用找钱。

题解:记得区分用r元和不用r元两种情况,分别对应模10的余数为r或者为0。现在枚举不超过10个就可以出结果。

B - Cormen --- The Best Friend Of a Man

题意:宠物狗每连续两天都需要总共走至少k步,注意对于[0,1]和[n,n+1]没有这个要求。给出一个数列表示第几天走几步,增加最少的步使得[1,2],[2,3]...[n-1,n]都满足每连续两天都需要总共走至少k步。

题解:贪心往右边的一天放。注意最后一天。

C - Sanatorium

题意:某人在食堂待了连续的一段时间,而每一天都依次吃早餐b、晚餐d、宵夜s,而他有可能会漏掉其中的一些餐。已知三种餐吃的次数,求最少漏了多少餐。

题解:可以分多种情况讨论,得到一个贪心:

假设他是从b开始吃,最后一餐吃b,则b会比另外两种多1。

假设他是从b开始吃,最后一餐吃d,则b和d会比s多1。

假设……

最后会发现一个规律,要把最少的两种都配到最多比最多的一种少1,而和他们的顺序无关(三种是完全对称的)。

*D - Exams

挺有意思的一道题。

题意:一段连续的日子,每个日子可能会有恰好一门课的Exam,或者没有任何Exam。问这段日子是否可以成功通过所有课的考试。注意每门课可能有多次Exam,只需要选一门完成。要是不参加当天的考试,则可以用来复习。第j门课在考试前需要aj天复习,问最短的通过所有考试的时间,或说明无解。

题解:一开始还在想怎么用堆(延迟决策贪心)来贪心,但是显然有个二分的算法,二分天数x,则每门课肯定选x及其之前的最后一次考试来考,这个可以O(n)得到,然后必定是贪心,到了选择的一门课的时候就要尽可能分配已有的复习资源给它,不够分配则GG。

int n, m;
int d[100005];
int a[100005];

pii lst[100005];

bool check(int len) {
    for(int i = 1; i <= m; ++i)
        lst[i] = {0, a[i]};
    for(int i = 1; i <= len; ++i)
        lst[d[i]].first = i;
    for(int i = 1; i <= m; ++i) {
        if(lst[i].first == 0)
            return 0;
    }
    sort(lst + 1, lst + 1 + m);
    int cnt0 = lst[1].first - 1;
    for(int i = 1; i <= m; ++i) {
        if(cnt0 < lst[i].second)
            return 0;
        else {
            if(i == m)
                return 1;
            cnt0 -= lst[i].second;
            cnt0 += (lst[i + 1].first - lst[i].first - 1);
        }
    }
    return 0;
}

int LB;
int bs() {
    int L = LB, R = n;
    while(1) {
        int M = (L + R) >> 1;
        if(L == M) {
            if(check(L))
                return L;
            if(check(R))
                return R;
            return -1;
        }
        if(check(M))
            R = M;
        else
            L = M + 1;
    }
}

bool vis[100005];

void test_case() {
    scanf("%d%d", &n, &m);
    for(int i = 1; i <= n; ++i)
        scanf("%d", &d[i]);
    int cnt = 0;
    LB = -1;
    for(int i = 1; i <= n; ++i) {
        if(!vis[d[i]]) {
            vis[d[i]] = 1;
            ++cnt;
            if(cnt == m) {
                LB = i;
                break;
            }
        }
    }
    if(LB == -1) {
        puts("-1");
        return;
    }
    for(int i = 1; i <= m; ++i)
        scanf("%d", &a[i]);
    printf("%d\n", bs());
}

原文地址:https://www.cnblogs.com/KisekiPurin2019/p/12285846.html

时间: 2024-12-10 13:36:04

Codeforces Round #377 (Div. 2)的相关文章

Codeforces Round #377 (Div. 2) 732A B C D E

蒟蒻只能打div 2 A题水,10和个位数的使用互不影响,所以直接在模10意义下做 1 #include<bits/stdc++.h> 2 using namespace std; 3 int k,r; 4 int main(){ 5 scanf("%d%d",&k,&r); 6 k=k%10; 7 for(int i=1;i<=100;i++){ 8 if(k*i%10==0||k*i%10==r) { 9 printf("%d\n&quo

Codeforces Round #377 (Div. 2) B. Cormen — The Best Friend Of a Man(贪心)

 传送门 Description Recently a dog was bought for Polycarp. The dog's name is Cormen. Now Polycarp has a lot of troubles. For example, Cormen likes going for a walk. Empirically Polycarp learned that the dog needs at least k walks for any two consecutiv

Codeforces Round #279 (Div. 2) ABCD

Codeforces Round #279 (Div. 2) 做得我都变绿了! Problems # Name     A Team Olympiad standard input/output 1 s, 256 MB  x2377 B Queue standard input/output 2 s, 256 MB  x1250 C Hacking Cypher standard input/output 1 s, 256 MB  x740 D Chocolate standard input/

Codeforces Round #428 (Div. 2)

Codeforces Round #428 (Div. 2) A    看懂题目意思就知道做了 #include<bits/stdc++.h> using namespace std; #pragma comment(linker, "/STACK:102400000,102400000") #define rep(i,a,b) for (int i=a; i<=b; ++i) #define per(i,b,a) for (int i=b; i>=a; --i

Codeforces Round #424 (Div. 2) D. Office Keys(dp)

题目链接:Codeforces Round #424 (Div. 2) D. Office Keys 题意: 在一条轴上有n个人,和m个钥匙,门在s位置. 现在每个人走单位距离需要单位时间. 每个钥匙只能被一个人拿. 求全部的人拿到钥匙并且走到门的最短时间. 题解: 显然没有交叉的情况,因为如果交叉的话可能不是最优解. 然后考虑dp[i][j]表示第i个人拿了第j把钥匙,然后 dp[i][j]=max(val(i,j),min(dp[i-1][i-1~j]))   val(i,j)表示第i个人拿

Codeforces Round #424 (Div. 2) C. Jury Marks(乱搞)

题目链接:Codeforces Round #424 (Div. 2) C. Jury Marks 题意: 给你一个有n个数序列,现在让你确定一个x,使得x通过挨着加这个序列的每一个数能出现所有给出的k个数. 问合法的x有多少个.题目保证这k个数完全不同. 题解: 显然,要将这n个数求一下前缀和,并且排一下序,这样,能出现的数就可以表示为x+a,x+b,x+c了. 这里 x+a,x+b,x+c是递增的.这里我把这个序列叫做A序列 然后对于给出的k个数,我们也排一下序,这里我把它叫做B序列,如果我

[Codeforces] Round #352 (Div. 2)

人生不止眼前的狗血,还有远方的狗带 A题B题一如既往的丝帛题 A题题意:询问按照12345678910111213...的顺序排列下去第n(n<=10^3)个数是多少 题解:打表,输出 1 #include<bits/stdc++.h> 2 using namespace std; 3 int dig[10],A[1005]; 4 int main(){ 5 int aa=0; 6 for(int i=1;;i++){ 7 int x=i,dd=0; 8 while(x)dig[++dd

Codeforces Round #273 (Div. 2)

Codeforces Round #273 (Div. 2) 题目链接 A:签到,仅仅要推断总和是不是5的倍数就可以,注意推断0的情况 B:最大值的情况是每一个集合先放1个,剩下都丢到一个集合去,最小值是尽量平均去分 C:假如3种球从小到大是a, b, c,那么假设(a + b) 2 <= c这个比較明显答案就是a + b了.由于c肯定要剩余了,假设(a + b)2 > c的话,就肯定能构造出最优的(a + b + c) / 3,由于肯定能够先拿a和b去消除c,而且控制a和b成2倍关系或者消除

Codeforces Round #339 (Div. 2) B. Gena&#39;s Code

B. Gena's Code It's the year 4527 and the tanks game that we all know and love still exists. There also exists Great Gena's code, written in 2016. The problem this code solves is: given the number of tanks that go into the battle from each country, f