Codeforces Round #500 (Div. 2) [based on EJOI]

Codeforces Round #500 (Div. 2) [based on EJOI]

https://codeforces.com/contest/1013

A

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define lson l,mid,rt<<1
 4 #define rson mid+1,r,rt<<1|1
 5 #define IT set<node>::iterator
 6 #define sqr(x) ((x)*(x))
 7 #define pb push_back
 8 #define eb emplace_back
 9 #define maxn 200005
10 #define eps 1e-8
11 #define pi acos(-1.0)
12 #define rep(k,i,j) for(int k=i;k<j;k++)
13 typedef long long ll;
14 typedef pair<int,int> pii;
15 typedef pair<ll,ll>pll;
16 typedef pair<ll,int> pli;
17 typedef pair<pair<int,string>,pii> ppp;
18 typedef unsigned long long ull;
19 const long long MOD=1e9+7;
20 const double oula=0.57721566490153286060651209;
21 using namespace std;
22
23
24 int n,ans1,ans2;
25
26 int main(){
27     std::ios::sync_with_stdio(false);
28     cin>>n;
29     int x;
30     for(int i=1;i<=n;i++){
31         cin>>x;
32         ans1+=x;
33     }
34     for(int i=1;i<=n;i++){
35         cin>>x;
36         ans2+=x;
37     }
38     if(ans1>=ans2) puts("YES");
39     else puts("NO");
40 }

B

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define lson l,mid,rt<<1
 4 #define rson mid+1,r,rt<<1|1
 5 #define IT set<node>::iterator
 6 #define sqr(x) ((x)*(x))
 7 #define pb push_back
 8 #define eb emplace_back
 9 #define maxn 200005
10 #define eps 1e-8
11 #define pi acos(-1.0)
12 #define rep(k,i,j) for(int k=i;k<j;k++)
13 typedef long long ll;
14 typedef pair<int,int> pii;
15 typedef pair<ll,ll>pll;
16 typedef pair<ll,int> pli;
17 typedef pair<pair<int,string>,pii> ppp;
18 typedef unsigned long long ull;
19 const long long MOD=1e9+7;
20 const double oula=0.57721566490153286060651209;
21 using namespace std;
22
23
24 int n,x;
25 int a[100005];
26 int b[100005];
27 set<int>se1,se2,se3;
28
29 int main(){
30     std::ios::sync_with_stdio(false);
31     cin>>n>>x;
32     for(int i=1;i<=n;i++){
33         cin>>a[i];
34         b[i]=a[i]&x;
35         se1.insert(a[i]);
36         se2.insert(b[i]);
37     }
38     if(se1.size()!=n){
39         cout<<0<<endl;
40         return 0;
41     }
42     for(int i=1;i<=n;i++){
43         se1.erase(a[i]);
44         se1.insert(b[i]);
45         if(se1.size()!=n){
46             cout<<1<<endl;
47             return 0;
48         }
49         se1.erase(b[i]);
50         se1.insert(a[i]);
51     }
52     if(se2.size()!=n){
53         cout<<2<<endl;
54         return 0;
55     }
56     cout<<-1<<endl;
57 }

C

题意:给你2*n个值,组成n个点,问能覆盖这n个点的最小矩形面积

思路:枚举长度为n的区间,这段区间作为x坐标的范围,然后将这段区间的差值与剩下部分的差值相乘取最小值

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define lson l,mid,rt<<1
 4 #define rson mid+1,r,rt<<1|1
 5 #define IT set<node>::iterator
 6 #define sqr(x) ((x)*(x))
 7 #define pb push_back
 8 #define eb emplace_back
 9 #define maxn 200005
10 #define eps 1e-8
11 #define pi acos(-1.0)
12 #define rep(k,i,j) for(int k=i;k<j;k++)
13 typedef long long ll;
14 typedef pair<int,int> pii;
15 typedef pair<ll,ll>pll;
16 typedef pair<ll,int> pli;
17 typedef pair<pair<int,string>,pii> ppp;
18 typedef unsigned long long ull;
19 const long long MOD=1e9+7;
20 const double oula=0.57721566490153286060651209;
21 using namespace std;
22
23
24 int n;
25 ll a[maxn];
26
27 int main(){
28     std::ios::sync_with_stdio(false);
29     cin>>n;
30     n*=2;
31     for(int i=1;i<=n;i++) cin>>a[i];
32     sort(a+1,a+n+1);
33     ll ans=(a[n/2]-a[1])*(a[n]-a[n/2+1]);
34     for(int i=2;i<=n/2+1;i++){
35         ans=min(ans,(a[n]-a[1])*(a[i+n/2-1]-a[i]));
36     }
37     cout<<ans<<endl;
38 }

D

题意:有一个n*m的矩形,一开始有q个格子上被标记。对于任意两行两列,如果交汇的四个格子中有三个被标记,那么第4个也会被标记。求至少需要手动标记几个格子,才能让整个矩形内的格子都被标记。

题意:当(x1,y1),(x1,y2),(x2,y1)被标记时,(x2,y2)也会被标记,所以用并查集维护,判断有多少个点是没有被标记的

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define lson l,mid,rt<<1
 4 #define rson mid+1,r,rt<<1|1
 5 #define IT set<node>::iterator
 6 #define sqr(x) ((x)*(x))
 7 #define pb push_back
 8 #define eb emplace_back
 9 #define maxn 200005
10 #define eps 1e-8
11 #define pi acos(-1.0)
12 #define rep(k,i,j) for(int k=i;k<j;k++)
13 typedef long long ll;
14 typedef pair<int,int> pii;
15 typedef pair<ll,ll>pll;
16 typedef pair<ll,int> pli;
17 typedef pair<pair<int,string>,pii> ppp;
18 typedef unsigned long long ull;
19 const long long MOD=1e9+7;
20 const double oula=0.57721566490153286060651209;
21 using namespace std;
22
23
24 int n,m,q;
25 int fa[maxn*2];
26
27 int Find(int x){
28     int r=x,y;
29     while(x!=fa[x]){
30         x=fa[x];
31     }
32     while(r!=x){
33         y=fa[r];
34         fa[r]=x;
35         r=y;
36     }
37     return x;
38 }
39
40 void join(int x,int y){
41     int xx=Find(x);
42     int yy=Find(y);
43     if(xx!=yy){
44         fa[xx]=yy;
45     }
46 }
47
48 int main(){
49     std::ios::sync_with_stdio(false);
50     cin>>n>>m>>q;
51     int x,y;
52     for(int i=1;i<=n+m;i++) fa[i]=i;
53     for(int i=1;i<=q;i++){
54         cin>>x>>y;
55         join(x,y+n);
56     }
57     int ans=0;
58     for(int i=1;i<=n+m;i++){
59         if(fa[i]==i){
60             ans++;
61         }
62     }
63     cout<<ans-1<<endl;
64 }

E

题意:给你n个数,你一次操作可以把某一个数减一,使任意k个数严格大于它旁边的两个数,问最少需要几次操作。输出1<=k<=(n+1)/2时的答案。

思路: dp[i][j][0]表示表示前i个数有j个满足条件,i、i-1都不满足条件的最少操作数

    dp[i][j][1]表示表示前i个数有j个满足条件,i满足条件的最少操作数

    dp[i][j][2]表示表示前i个数有j个满足条件,i-1满足条件的最少操作数

然后进行状态转移:

  dp[i][j][2]=dp[i-1][j][1]+max(0,a[i]-a[i-1]+1);
  dp[i][j][0]=min(dp[i-1][j][0],dp[i-1][j][2]);
  dp[i][j][1]=min(dp[i-1][j-1][0]+max(0,a[i-1]-a[i]+1),dp[i-1][j-1][2]+max(0,min(a[i-1],a[i-2]-1)-a[i]+1));

dp[i][j][1]分为两种情况:

1、前两个都不满足条件,那么i-1就是原来的数,即没有被操作过,需要的操作数就是max(0,a[i-1]-a[i]+1)

2、i-2满足条件,那么i-1已经变成了min(a[i-1],a[i-2]-1),还需要的操作数就是max(0,min(a[i-1],a[i-2]-1)-a[i]+1)

因为转移只用到了dp[i-1][j],dp[i-1][j-1],所以可以用滚动数组优化

参考博客:https://ouuan.blog.luogu.org/solution-cf1012c

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define lson l,mid,rt<<1
 4 #define rson mid+1,r,rt<<1|1
 5 #define IT set<node>::iterator
 6 #define sqr(x) ((x)*(x))
 7 #define pb push_back
 8 #define eb emplace_back
 9 #define maxn 200005
10 #define eps 1e-8
11 #define pi acos(-1.0)
12 #define rep(k,i,j) for(int k=i;k<j;k++)
13 typedef long long ll;
14 typedef pair<int,int> pii;
15 typedef pair<ll,ll>pll;
16 typedef pair<ll,int> pli;
17 typedef pair<pair<int,string>,pii> ppp;
18 typedef unsigned long long ull;
19 const long long MOD=1e9+7;
20 const double oula=0.57721566490153286060651209;
21 using namespace std;
22
23
24 int n;
25 int dp[2505][3];
26 int a[5005];
27
28 int main(){
29     std::ios::sync_with_stdio(false);
30     cin>>n;
31     for(int i=1;i<=n;i++) cin>>a[i];
32     for(int i=0;i<=2;i++){
33         for(int j=0;j<=(n+1)/2;j++){
34             dp[j][i]=0x3f3f3f3f;
35         }
36     }
37     dp[0][0]=dp[1][1]=0;
38     for(int i=2;i<=n;i++){
39         for(int j=(i+1)/2;j>=1;j--){
40             dp[j][2]=dp[j][1]+max(0,a[i]-a[i-1]+1);
41             dp[j][0]=min(dp[j][0],dp[j][2]);
42             dp[j][1]=min(dp[j-1][0]+max(0,a[i-1]-a[i]+1),dp[j-1][2]+max(0,min(a[i-1],a[i-2]-1)-a[i]+1));
43         }
44     }
45     for(int i=1;i<=(n+1)/2;i++){
46         cout<<min(dp[i][0],min(dp[i][1],dp[i][2]))<<" ";
47     }
48 }

原文地址:https://www.cnblogs.com/Fighting-sh/p/10595566.html

时间: 2024-11-08 18:13:08

Codeforces Round #500 (Div. 2) [based on EJOI]的相关文章

【cf比赛记录】Codeforces Round #606 (Div. 2, based on Technocup 2020 Elimination Round 4)

比赛传送门 只能说当晚状态不佳吧,有点头疼感冒的症状.也跟脑子没转过来有关系,A题最后一步爆搜没能立即想出来,B题搜索没有用好STL,C题也因为前面两题弄崩了心态,最后,果然掉分了. A:简单数学 B:数学+排序 C:字符串搜索 A // https://codeforces.com/contest/1277/problem/A /* 题意: 给出一个数,求不大于该数的完美整数的个数(完美整数指全是一个数组成的数字,如:111, 333333, 444444, 9, 8888 ...) 分析:

Codeforces Round #403 (Div. 1, based on Technocup 2017 Finals)

Div1单场我从来就没上过分,这场又剧毒,半天才打出B,C挂了好几次最后还FST了,回紫了. AC:AB Rank:340 Rating:2204-71->2133 Div2.B.The Meeting Place Cannot Be Changed 题目大意:n个人,第i个人位于xi,速度为vi,找到一个点使得所有人到这个点的耗时最小,输出耗时.(n<=60000) 思路:二分答案,知道耗时后可以求出每个人能到达的区间,如果所有区间有交则合法,复杂度O(nlog). #include<

Codeforces Round #437 (Div. 2, based on MemSQL Start[c]UP 3.0 - Round 2) E. Buy Low Sell High [贪心 II][数据结构 I]

题目:http://codeforces.com/contest/867/problem/E 题意:模拟股票操作,每天只能买一只股票或者卖一只股票或者什么也不做,求最大利润. 题解:仔细想想是非常简单的一个贪心问题,理解为连续的多次贪心买入卖出可以合并为一次的买入卖出,且值为最优.只需要用一个最小堆每次寻找前面的最小且没有被标记为购买点的值即可.如果自己为最小值,continue.如果那个值没有被选过,为买入点,pop.如果那个值被选为了售出的点,那么取消售出的标记,把当前点标记为售出点,利润直

Codeforces Round #500 (Div. 2) BC

CodeForces 1013B And CodeForces 1013C  Photo of The Sky B 可以发现只有一次与操作是有意义的,所以答案只有-1,0,1,2四种情况 1 #include <bits/stdc++.h> 2 #define show(a) cout << #a << " = " << a << endl; 3 const int MOD = 1e9+7; 4 const int MAXN

D. Arpa and a list of numbers Codeforces Round #432 (Div. 2, based on IndiaHacks Final Round 2017)

http://codeforces.com/contest/851/problem/D 分区间操作 1 #include <cstdio> 2 #include <cstdlib> 3 #include <cmath> 4 #include <cstring> 5 #include <time.h> 6 #include <string> 7 #include <set> 8 #include <map> 9

[Codeforces Round #522 (Div. 2, based on Technocup 2019 Elimination Round 3)][C. Playing Piano]

http://codeforces.com/contest/1079/problem/C 题目大意:给出一个数列a[n],让构造一个满足下列条件的数列b[n]:如果a[i]>a[i-1]那么b[i]>b[i-1],如果a[i]<a[i-1]那么b[i]<b[i-1],如果a[i]==a[i-1],那么b[i]!=b[i-1].其中1<=b[i]<=5  1<=a[i]<=2*1e5. 题解:dp[i][j]表示在位置i处取j时是否成立,如果成立则dp[i][

Codeforces Round #602 (Div. 2, based on Technocup 2020 Elimination Round 3

A,有多个线段,求一条最短的线段长度,能过覆盖到所又线段,例如(2,4)和(5,6) 那么我们需要4 5连起来,长度为1,例如(2,10)(3,11),用(3,10) 思路:我们想一下如果题目说的是最长我们肯定是取最小x和最大的y连起来就完事. 但是要求长度最小又得覆盖,那么可以这样想,我们需要把最小的x不断右移到这条线段的y, 最大的左移到x,所以就是最大x-最小y完事 #include <bits/stdc++.h> using namespace std; #define ll long

Codeforces Round #623 (Div. 2, based on VK Cup 2019-2020 - Elimination Round, Engine)

题目链接:https://codeforces.com/contest/1315 A - Dead Pixel 诚心诚意的送分题. 题意:给一个n*m的格子矩阵,和一个坏掉的格子,找一个最大的不包含坏掉的格子的矩阵. void test_case() { int n, m, x, y; scanf("%d%d%d%d", &n, &m, &x, &y); int ans = max(x * m, (n - (x + 1)) * m); ans = max

Codeforces Round #432 (Div. 2, based on IndiaHacks Final Round 2017) A

Arpa is researching the Mexican wave. There are n spectators in the stadium, labeled from 1 to n. They start the Mexican wave at time 0. At time 1, the first spectator stands. At time 2, the second spectator stands. ... At time k, the k-th spectator