2020.06.0 1 习题训练4
Posted emhhbw
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了2020.06.0 1 习题训练4相关的知识,希望对你有一定的参考价值。
题目链接:https://vjudge.net/problem/CodeForces-1330A
思路:
题目咋一读,很迷,其实就是说,给你现有n个数让你再添加 x 个数,使得数组中有最长化的 1~m 。所以这里就想到用map记录原先有的数,再从1开始寻找最长可到的数。
解题代码:
// .--------------. // | Try First One| // ‘--------------‘ // | .--------------. // | | | // V V | // .--------------. | // | AC. |<---. | // ‘--------------‘ | | // (True)| |(False) | | // .--------‘ | | | // | V | | // | .--------------. | | // | | Try Again |----‘ | // | ‘--------------‘ | // | | // | .--------------. | // ‘->| Try Next One |-------‘ // ‘--------------‘ #include <cstdio> #include <iostream> #include <algorithm> #include <cmath> #include <string> #include <cstring> #include <map> using namespace std; const long long N = 1e10 + 7; const int maxn = 2e5 + 5; const long long INF = 8e18; typedef long long ll; #define for0(i,n) for(int i = 0;i < n;i++) #define for1(i,n) for(int i = 1;i <= n;i++) map<int,int>ma; int main() { int t; cin >> t; while(t--){ int n,x; cin >> n >> x; for0(i,n){ int m; cin >> m; ma[m]++; } int temp = 1; while(1){ if( !(x > 0) && ma[temp]==0) break; if(ma[temp++]==0){ x--; } } cout << temp-1 << endl; ma.clear(); } return 0; }
题目链接:https://vjudge.net/problem/CodeForces-1332A
思路:
给出当前位置坐标,给出边界坐标,给出必须要往某个方向前进的次数。问能否实现。这里可以先对方向进行抵消(然而这里要注意当当行列为一条线时,是不能抵消的,当初就被坑了),抵消完,再当前坐标到对应方向的距离关系判断是否可以实现。
解题代码:
#include <cstdio> #include <iostream> #include <algorithm> #include <cmath> #include <string> #include <cstring> using namespace std; const long long N = 1e10 + 7; const int maxn = 2e5 + 5; const long long INF = 8e18; typedef long long ll; #define for0(i,n) for(int i = 0;i < n;i++) #define for1(i,n) for(int i = 1;i <= n;i++) int main() { int t; cin >> t; while(t--){ int a,b,c,d; int x,y,x1,y1,x2,y2; int sign1 = 1; cin >> a >> b >> c >> d >> x >> y >> x1 >> y1 >> x2 >> y2; if(x>x1 || x<x2){ int l = min(a,b); a -= l; b -= l; } if(y>y1 || y<y2){ int l = min(c,d); c -= l; d -= l; } if( (x - x1) < a || (x2 - x) < b || (y - y1) < c || (y2 - y) < d ){ sign1 = 0; } if(sign1) cout << "Yes" << endl; else cout << "No" << endl; } return 0; }
题目链接:https://vjudge.net/problem/CodeForces-1332A
思路:
题目给出 n 个数(小于1000),保证这些数肯定能被素数整除,能被相同素数整除的涂相同颜色(也可以不相同,但是简化肯定是涂成相同的),问一种符合条件的涂法,所用颜色种类小于12。这里提到每个数小于1000,而且颜色最多用11种,也就是最多有11个素数做除数的情况,所以可以对每个数去除这11个素数,并将相同类标记好。
解题代码:
// .--------------. // | Try First One| // ‘--------------‘ // | .--------------. // | | | // V V | // .--------------. | // | AC. |<---. | // ‘--------------‘ | | // (True)| |(False) | | // .--------‘ | | | // | V | | // | .--------------. | | // | | Try Again |----‘ | // | ‘--------------‘ | // | | // | .--------------. | // ‘->| Try Next One |-------‘ // ‘--------------‘ #include <cstdio> #include <iostream> #include <algorithm> #include <cmath> #include <string> #include <cstring> #include <map> using namespace std; const long long N = 1e10 + 7; const int maxn = 2e5 + 5; const long long INF = 8e18; typedef long long ll; #define for0(i,n) for(int i = 0;i < n;i++) #define for1(i,n) for(int i = 1;i <= n;i++) int sign[1010],a[1010],b[1010]; int prime[11] = {2,3,5,7,11,13,17,19,23,29,31}; int main() { int t; cin >> t; while(t--){ int n,temp = 1; cin >> n; for0(i,n) cin >> a[i]; for0(i,n){ for(int j = 0;j < 11;j++){ if(a[i] % prime[j] == 0){ if(sign[j] == 0) sign[j] = temp++; b[i] = sign[j]; break; } } } cout << temp-1 << endl; for0(i,n){ cout << b[i] << " "; } cout << endl; memset(sign,0,sizeof(sign)); } return 0; }
题目链接:https://vjudge.net/problem/CodeForces-1328B
思路:
一个由2个 ‘b’ ,n-2 个 ‘a’ 构成的字符串,按字符串排序,询问排在第 k 个字符串是什么。这个题就是要确定b的位置,通过题目给出的一个排序,可以注意到,当倒数第2个 ‘b‘ 在倒数第二个时有一个情况,在倒数第三个时由两个情况,在倒数第四个时三个情况。所以可以通过给出的 k 先确定一个 ‘b‘ ,再去确定最后一个 ‘b’ 。
解题代码:
// .--------------. // | Try First One| // ‘--------------‘ // | .--------------. // | | | // V V | // .--------------. | // | AC. |<---. | // ‘--------------‘ | | // (True)| |(False) | | // .--------‘ | | | // | V | | // | .--------------. | | // | | Try Again |----‘ | // | ‘--------------‘ | // | | // | .--------------. | // ‘->| Try Next One |-------‘ // ‘--------------‘ #include <cstdio> #include <iostream> #include <algorithm> #include <cmath> #include <string> #include <cstring> #include <map> using namespace std; const long long N = 1e10 + 7; const int maxn = 2e5 + 5; const long long INF = 8e18; typedef long long ll; #define for0(i,n) for(int i = 0;i < n;i++) #define for1(i,n) for(int i = 1;i <= n;i++) ll sum[100010]; int main() { for(int i=1;i <= 100005;i++){ sum[i] = sum[i-1] + i; } int t; cin >> t; while(t--){ int n,num,i; cin >> n >> num; string s(n, ‘a‘); for(i = 1;;i++){ if(sum[i] >= num ) break; } s[n-1 - i] = ‘b‘; int num2 = num - sum[i-1]; s[n-1 -(num2-1)] = ‘b‘; cout << s << endl; } return 0; }
题目链接:https://vjudge.net/problem/CodeForces-1328D
思路:
给出长度为 n 的一个数组,并将首尾连接,变成圆环,进行染色操作。相邻的不同种类的不能用相同颜色,如果相邻种类相同,无限制,要求最小化所用颜色种类。这里想到当给出的数组全为同一个数时,肯定只需要1种颜料就可以了。当n为偶数时,一直使相邻两个颜色交替,头尾也不一样。当n为奇数时,这样相邻两个颜色交替安排的话头尾肯定会出现相同颜色,当中途有两个相同的数相邻(要注意头尾相同时,也是相邻要考虑的情况,当初没考虑WA了,找了好久),可以通过这里改变交替顺序,这样又可以保证用两个颜色也可涂,反之则只能把尾部的涂成第3种颜色。
解题代码:
// .--------------. // | Try First One| // ‘--------------‘ // | .--------------. // | | | // V V | // .--------------. | // | AC. |<---. | // ‘--------------‘ | | // (True)| |(False) | | // .--------‘ | | | // | V | | // | .--------------. | | // | | Try Again |----‘ | // | ‘--------------‘ | // | | // | .--------------. | // ‘->| Try Next One |-------‘ // ‘--------------‘ #include <cstdio> #include <iostream> #include <algorithm> #include <cmath> #include <string> #include <cstring> #include <map> using namespace std; const long long N = 1e10 + 7; const int maxn = 2e5 + 5; const long long INF = 8e18; typedef long long ll; #define for0(i,n) for(int i = 0;i < n;i++) #define for1(i,n) for(int i = 1;i <= n;i++) int a[200100]; int main() { int t; cin >> t; while(t--){ int n,point = 0,sign = 1; cin >> n; for1(i,n){ cin >> a[i]; if(a[i] == a[i-1] && !point) point = i; if(i != 1 && a[i] != a[i-1]){ sign = 0; } } if(sign){ cout << 1 << endl; for1(i,n){ cout << 1 << " "; } cout << endl; continue; } if(n % 2 == 0){ cout << 2 << endl; for1(i,n){ if(i%2) cout << 1 << " "; else cout << 2 << " "; } } else if(n%2 && point){ cout << 2 << endl; for1(i,point-1){ if(i%2) cout << 1 << " "; else cout << 2 << " "; } for(int i = point;i <= n;i++){ if(i % 2) cout << 2 << " "; else cout << 1 << " "; } } else{ if(a[n] == a[1]) cout << 2 << endl; else cout << 3 << endl; for1(i,n-1){ if(i % 2) cout << 1 << " "; else cout << 2 << " "; } if(a[n] == a[1]) cout << 1; else cout << 3; } cout << endl; } return 0; }
以上是关于2020.06.0 1 习题训练4的主要内容,如果未能解决你的问题,请参考以下文章