Codeforces Round #396 (Div. 2)
传送门:http://codeforces.com/contest/766
A题:给你两个字符串,求两个字符串的最大非公共子串长度。假设
#include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #include <vector> #include <queue> #include <string> #include <stack> #include <map> #include <set> #include <bitset> #define X first #define Y second #define clr(u,v); memset(u,v,sizeof(u)); #define in() freopen("data","r",stdin); #define out() freopen("ans","w",stdout); #define Clear(Q); while (!Q.empty()) Q.pop(); #define pb push_back using namespace std; typedef long long ll; typedef pair<int, int> pii; const int maxn = 1e5 + 10; const int INF = 0x3f3f3f3f; int main() { string s1, s2; cin >> s1 >> s2; if (s1 == s2) cout << -1 << endl; else cout << max(s1.length(), s2.length()) << endl; return 0; }
B题:给你n条线段,问能不能找到三条线段组成一个三角形。考虑三条边a,b,c有a<=b=<c,只要保证a+b>c>b-a就行了,事实上只要保证a+b>c就可以,假设c<=b-a,则a+c<=b<c,=>a<0矛盾,所以只要保证a+b>c就好,那a+b要尽可能大,所以肯定是恰好小于等于c的两个线段,所以直接对线段进行排序,扫一遍找到有N[i]<N[i-1]+N[i-2]的线段就行了。
#include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #include <vector> #include <queue> #include <string> #include <stack> #include <map> #include <set> #include <bitset> #define X first #define Y second #define clr(u,v); memset(u,v,sizeof(u)); #define in() freopen("data","r",stdin); #define out() freopen("ans","w",stdout); #define Clear(Q); while (!Q.empty()) Q.pop(); #define pb push_back using namespace std; typedef long long ll; typedef pair<int, int> pii; const int maxn = 1e5 + 10; const int INF = 0x3f3f3f3f; int N[maxn]; int main() { int n; scanf("%d", &n); for (int i = 0; i < n; i++) scanf("%d", &N[i]); sort(N, N + n); for (int i = 2; i < n; i++) { if (N[i] < N[i-1] + N[i-2]) { puts("YES"); return 0; } } puts("NO"); return 0; }
C题:给你一个长度为n的字符串str,以及数组a,ax表示字符x只能出现在长度为ax以内的字符串里,现在要求对字符串进行合法分隔,问有多少种分隔方法,并输出分隔出的字符串最长长度,以及分隔最少个数。这题直接xjb dp做的,dp[i]表示以i作为分界点的方案数,那么我们找下标小于i的,满足Minax<len的位置加起来,就是dp[i]了,具体还是看代码吧。至于最长长度和最少个数在dp的时候顺便更新一下就好了。
#include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #include <vector> #include <queue> #include <string> #include <stack> #include <map> #include <set> #include <bitset> #define X first #define Y second #define clr(u,v); memset(u,v,sizeof(u)); #define in() freopen("data","r",stdin); #define out() freopen("ans","w",stdout); #define Clear(Q); while (!Q.empty()) Q.pop(); #define pb push_back using namespace std; typedef long long ll; typedef pair<int, int> pii; const int maxn = 1e3 + 10; const int INF = 0x3f3f3f3f; const int mod = 1e9 + 7; int dp[maxn]; int c[30]; char str[maxn]; int Mincnt[maxn]; int main() { clr(Mincnt, 0x3f); int n; scanf("%d", &n); scanf("%s", str + 1); for (int i = 0; i < 26; i++) scanf("%d", &c[i]); dp[0] = 1; Mincnt[0] = 0; int Maxlen = 0; for (int i = 1; i <= n; i++) { int Min = c[str[i] - 'a'], len = 1; for (int j = i - 1; j >= 0; j--) { len++; Min = min(Min, c[str[j] - 'a']); dp[i] = (dp[j] + dp[i]) % mod; Mincnt[i] = min(Mincnt[i], Mincnt[j] + 1); if (Min < len) break; } Maxlen = max(Maxlen, len - 1); } // for (int i=0;i<=n;i++) cout<<dp[i]<<endl; cout << dp[n] << endl; cout << Maxlen << endl; cout << Mincnt[n] << endl; return 0; }
D题:给你n个单词,并给出m组操作,把单词归为同类和不同类,注意不同类的不同类就是同一类。再有q组查询,查询单词之间的关系。这题和之前做过的一题很类似,其实就是个并查集,具体查看:http://www.cnblogs.com/scaugsh/p/5533202.html 跟这题差不多,就是把id和id+n当作不同关系后直接并查集就行了。
#include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> #include <vector> #include <queue> #include <string> #include <stack> #include <map> #include <set> #include <bitset> #define X first #define Y second #define clr(u,v); memset(u,v,sizeof(u)); #define in() freopen("data","r",stdin); #define out() freopen("ans","w",stdout); #define Clear(Q); while (!Q.empty()) Q.pop(); #define pb push_back using namespace std; typedef long long ll; typedef pair<int, int> pii; const int maxn = 2e5 + 10; const int INF = 0x3f3f3f3f; int n, m, q, t; int f[maxn]; void init() { for (int i = 0; i <= 2 * n; i++) f[i] = i; } int find(int x) { return f[x] == x ? x : f[x] = find(f[x]); } void mix(int x, int y) { int fx = find(x), fy = find(y); f[fx] = fy; } map <string, int> M; int main() { //ios::sync_with_stdio(false); cin >> n >> m >> q; init(); int cnt = 0; for (int i = 0; i < n; i++) { string str; cin >> str; M[str] = cnt++; } while (m--) { cin >> t; string str1, str2; cin >> str1 >> str2; if (t == 1) { int id1 = M[str1], id2 = M[str2]; if (find(id1) == find(id2 + n) || find(id1 + n) == find(id2)) { cout << "NO" << endl; continue; } cout << "YES" << endl; mix(id1, id2), mix(id1 + n, id2 + n); } else { int id1 = M[str1], id2 = M[str2]; if (find(id1) == find(id2) || find(id1 + n) == find(id2 + n)) { cout << "NO" << endl; continue; } cout << "YES" << endl; mix(id1 + n, id2), mix(id1, id2 + n); } } while (q--) { string str1, str2; cin >> str1 >> str2; int id1 = M[str1], id2 = M[str2]; if (find(id1) == find(id2) || find(id1 + n) == find(id2 + n)) cout << 1 << endl; else if (find(id1) == find(id2 + n) || find(id1 + n) == find(id2)) cout << 2 << endl; else cout << 3 << endl; } return 0; }
这场四题还不算难,不过ab题题意理解难度增加了,b题还看题题意导致花了好长时间= =不过无所谓,反正我做的是虚拟竞赛
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~