Codeforces Round #515 (Div. 3) 解题报告(A~E)

题目链接:http://codeforces.com/contest/1066

A题:

题意:Vova想坐火车从1点到L点,在路上v的整数倍的点上分布着灯笼,而在路上从l到r处停着别的火车,它挡着Vova的视线使他看不到灯笼。给定L,v,l,r求Vova能看到的灯笼数。

分析:从1到x上所有的灯笼数量为x/v个。则路上所有的灯笼数为L/v个,被挡住的则为 r/v - (l-1)/v 个,相减即为答案。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<string>
#include<queue>
#include<vector>
#include<set>
#include<map>
#define closeio std::ios::sync_with_stdio(false)
using namespace std;
typedef long long ll;
int t,L,v,l,r;
int main()
{
    cin>>t;
    while(t--)
    {
        scanf("%d%d%d%d",&L,&v,&l,&r);
        int ans = L / v;
        ans = ans - (r/v - (l-1)/v);
        cout<<ans<<endl;
    }
    return 0;
}

B题:

题意:Vova的房子由从1到n的房间组成。这些房间从左到右排成一排相互连通,有的房间放着火炉。火炉工作时可以温暖以其所在的第pos个房间为中心, [pos−r+1;pos+r−1]这个区间的所有房间。现在给定n个房间的火炉信息和r,求最少需要开几个火炉可以使整个房子都温暖。

分析:贪心,例如对于起始点1来说,在能覆盖到点1的所有火炉中,我们选最靠后的那一个。之后的每次处理就是把新的第一个没有覆盖到的点看成起始点继续贪心。这样可以保证每次选择覆盖的区间尽可能大。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<string>
#include<queue>
#include<vector>
#include<set>
#include<map>
#define closeio std::ios::sync_with_stdio(false)
using namespace std;
const int maxn = 20005;
int n,r,a[maxn],ans;
bool flag;
int main()
{
    int i,j;
    while(cin>>n>>r)
    {
        flag = true;
        memset(a,0,sizeof(a));
        for(i=1;i<=n;i++)
        scanf("%d",&a[i]);
        int pos = 0;//pos指向最后放置的炉子的位置
        for(i = r;i >= 1; i--)
        {
            if(a[i] == 1)
            {
                pos = i;
                ans = 1;
                break;
            }
        }
        if(i == 0) flag = false;
        while(pos + r - 1 < n && flag)//pos+r-1是当前所放最后一个炉子能覆盖的最右点
        {
            for(i = pos+r*2-1;i >= pos; i--)//pos+r*2-1是下一个炉子可以存在的位置的最远点,注意这里值可能比1000大,所以数组范围开大些
            {
                if(a[i] == 1)
                {
                    if(i == pos) //pos后的长度为2*r-1的区间没有炉子
                        flag = false;
                    else
                    {
                        pos = i;
                        ans ++;
                    }
                    break;
                }
            }
        }
        printf("%d\n",flag?ans:-1);
    }
    return 0;
}

C题:

题意:你有一个书架,可以对它进行三种操作:L id表示把编号为id的书放在所有书的最左边。R id表示表示把编号为id的书放在所有书的最右边。? id表示询问编号为id的书距离整个书列的最外侧(左侧或右侧)的最小值。

分析:题目给定的操作数量和id的范围均为2*1e5,所以可以开一个2*1e5大小的数组存放每本书的位置。我们可以设置posx和posy分别指向书列的左右两侧的位置,当有书放进来时改变posx和posy的值并赋给a[id],查询操作如上所述。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<string>
#include<queue>
#include<vector>
#include<set>
#include<map>
#define closeio std::ios::sync_with_stdio(false)
using namespace std;
const int maxn = 200005;
int a[maxn],id,q,posx,posy;
char c;
int main()
{
    cin>>q;
    posx = posy = 0;
    memset(a,0,sizeof(a));
    while(q--)
    {
        getchar();
        scanf("%c %d",&c,&id);
        if(c == ‘L‘)
        {
            a[id] = posx--;
        }
        if(c == ‘R‘)
        {
            a[id] = ++posy;
        }
        if(c == ‘?‘)
        {
            cout<<min(a[id] - posx - 1,posy - a[id])<<endl;
        }
    }
    return 0;
}

D题:

题意:这个题的题意很蛋疼QAQ不想扯,出题人就是想通过题意把你带跑。其实是最简单的一个题,就是给你n个物品,让你放进m个容量为k的箱子里,要求是只能取从最后一个开始连续的物品,问最多装几个物品。

分析:直接从后往前扫一遍得出答案。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<string>
#include<queue>
#include<vector>
#include<set>
#include<map>
#define closeio std::ios::sync_with_stdio(false)
using namespace std;
const int maxn = 200005;
int n,m,k,ans,pos;
int a[maxn],b[maxn];
int main()
{
    int i,j;
    while(cin>>n>>m>>k)
    {
        for(i = 1;i <= n; i++)
            scanf("%d",&a[i]);
        for(i = 1;i <= m;i++)
            b[i] = k;
        j = m;
        ans = 0;
        for(i = n;i >= 1; i--)
        {
            if(b[j] >= a[i])
            {
                b[j] -= a[i];
                ans ++;
            }
            else
            {
                if(j > 1)
                {
                    b[--j] -= a[i];
                    ans ++;
                }
                else
                {
                    break;
                }
            }
        }
        cout<<ans<<endl;
    }
    return 0;
}

E题:

题意:给你长为n的二进制数a和长为m的二进制数b,每次操作把a&b的十进制结果累加起来,然后把b往右移一位直到b为0。最后结果对998244353998244353取余。

分析:这个题还是非常不错的一道题的。对于a的每一个为1的二进制位,其对答案的贡献就是所有a&b操作后a的这一位仍为1的次数再乘上这一位为1对应的十进制数。所以我们预处理一下pw数组存放二进制位为1对应的10进制数取余,sum数组则存放前缀和,sum[i]即为第i位及其之前b里有几个1。考虑到n与m可能不相等,我们预处理一下a,b使其长度一致。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<string>
#include<queue>
#include<vector>
#include<set>
#include<map>
#define closeio std::ios::sync_with_stdio(false)
using namespace std;
typedef long long ll;
const ll mod = 998244353;
const int maxn = 200005;
ll n,m,pw[maxn],sum[maxn];
string a,b;
void init_ab()
{
    if(n > m) b = string(n-m,‘0‘) + b;
    else if(m>n) a = string(m-n,‘0‘) + a;

    memset(sum,0,sizeof(sum));
    memset(pw,0,sizeof(0));

    int i,j;
    pw[0] = 1;
    for(i = 1;i < maxn; i++) pw[i] = pw[i-1] * 2 % mod;//预处理pw数组
}
int main()
{
    int i,j,k;
    while(cin>>n>>m)
    {
        ll ans = 0;
        closeio;
        a.clear();
        b.clear();
        cin>>a>>b;
        init_ab();
        k = max(n,m);
        sum[0] = b[0]==‘1‘;
        for(i = 1;i < k;i++)
            sum[i] = sum[i-1] + (b[i] == ‘1‘);//sum[i]存放第i位及其之前b里有多少位为1
        for(i = 0;i < k;i ++)
        {
            if(a[i]-‘0‘)//a[i]为1才对答案有贡献
            {
                ans = (ans + pw[k-i-1] * sum[i] % mod) % mod;//所有a&b操作后a的这一位仍为1的次数再乘上这一位为1对应的十进制数
            }
        }
        cout<<ans<<endl;
    }
    return 0;
}

原文地址:https://www.cnblogs.com/chdforestsea/p/9788956.html

时间: 2024-11-08 06:15:43

Codeforces Round #515 (Div. 3) 解题报告(A~E)的相关文章

Codeforces Round #259 (Div. 2) 解题报告

终于重上DIV1了.... A:在正方形中输出一个菱形 解题代码: 1 // File Name: a.cpp 2 // Author: darkdream 3 // Created Time: 2014年08月01日 星期五 23时27分55秒 4 5 #include<vector> 6 #include<set> 7 #include<deque> 8 #include<stack> 9 #include<bitset> 10 #inclu

Codeforces Round #262 (Div. 2)解题报告

详见:http://robotcator.logdown.com/posts/221514-codeforces-round-262-div-2 1:A. Vasya and Socks   http://codeforces.com/contest/460/problem/A 有n双袜子,每天穿一双然后扔掉,每隔m天买一双新袜子,问最多少天后没有袜子穿.. 简单思维题:以前不注重这方面的训练,结果做了比较久,这种题自己边模拟边想.不过要多考虑trick ```c++ int main(){ i

Codeforces Round #616 (Div. 2)解题报告

Codeforces Round #616 (Div. 2)解题报告 A. Even But Not Even 找两个奇数就行了. #include<bits/stdc++.h> using namespace std; void solve() { int n; string s; cin >> n >> s; string ans = ""; for(int i = 0; i < n; i++) { if(int(s[i] - '0')%2

Codeforces Round #479 (Div. 3)解题报告

题目链接: http://codeforces.com/contest/977 A. Wrong Subtraction 题意 给定一个数x,求n次操作输出.操作规则:10的倍数则除10,否则减1 直接写,手速题,没啥好说的 B. Two-gram 题意 求出现次数最多的连续两个字符 还是签到题,我居然很麻烦地用了map,= =算了,思路畅通都无所谓了 #include <iostream> #include<stdio.h> #include<algorithm> #

Codeforces Round #401 (Div. 2)解题报告

A - Shell Game 1 #include <iostream> 2 #include<bits/stdc++.h> 3 #include <stack> 4 #include <queue> 5 #include <map> 6 #include <set> 7 #include <cstdio> 8 #include <cstring> 9 #include <algorithm> 10

Codeforces Round #390 (Div. 2) 解题报告

时隔一个月重返coding…… 期末复习了一个月也不亏 倒是都过了…… 就是计组61有点亏 复变68也太低了 其他都还好…… 假期做的第一场cf 三道题 还可以…… 最后room第三 standing383简直人生巅峰…… 看楼上楼下都是两道题的 如果A题不错那么多估计能进前300了吧…… 这场倒是把之前两场的分加回来了 开头不错 这个假期争取紫名~ A.Lesha and array splitting 把给定的数组分割成几个区间 要求各个区间和不能为0 一开始没注意到分割之后的区间重新合成之

Codeforces Round #394 (Div. 2) 解题报告

开始补题,今天下午virtual参赛,过了ABC,D题因为一点小错误而没能在比赛时间中AC,时间到了之后几分钟就发现了问题所在,略有遗憾.之后一直冥思苦想E题,在提示下终于明白,真的是给这样组合题画风的题目跪了,只能说继续加油,扩展思路吧. A题 题目地址 只有奇偶数个数相差小于等于1时可以,需要特判不能使二者均为0的情况. 参考代码 1 #include<stdio.h> 2 #include<bits/stdc++.h> 3 #include <iostream>

Codeforces Round #279 (Div. 2) 解题报告

A - Team Olympiad 贪心水题..都从第一个开始取即可. 代码如下: #include <iostream> #include <cstdio> #include <string> #include <cstring> #include <stdlib.h> #include <math.h> #include <ctype.h> #include <queue> #include <map

Codeforces Round #395 (Div. 2) 解题报告

年后恢复训练参加的第一场,表现的不是很好,必须要赶紧振作起来了啊. A.B题不再赘述. C题 不要被树的形式吓到,实际上不需要换根DFS,只需要看两顶点颜色不同的线段即可. 1 #include<stdio.h> 2 #include<bits/stdc++.h> 3 #include <iostream> 4 using namespace std; 5 typedef long long ll; 6 typedef unsigned long long ull; 7