A
#include <bits/stdc++.h> #define PI acos(-1.0) #define mem(a,b) memset((a),b,sizeof(a)) #define TS printf("!!! ") #define pb push_back #define inf 1e9 //std::ios::sync_with_stdio(false); using namespace std; //priority_queue<int,vector<int>,greater<int>> que; get min const double eps = 1.0e-8; typedef pair<int, int> pairint; typedef long long ll; typedef unsigned long long ull; const int maxn = 3e7 + 10; const int maxm = 300; const int turn[4][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}}; //priority_queue<int, vector<int>, less<int>> que; //next_permutation ll mod = 1e9 + 7; int main() { int x, y; cin >> x >> y; if (x == 0 || y == 0) { if (x == 0 && y == 1) { cout << "Yes" << endl; } else { cout << "No" << endl; } return 0; } int cur = y - 1; int remain = x - cur; if (remain % 2 == 0 && cur && remain>=0) { cout << "Yes" << endl; return 0; } cout << "No" << endl; return 0; }
B
#include <bits/stdc++.h> #define PI acos(-1.0) #define mem(a,b) memset((a),b,sizeof(a)) #define TS printf("!!! ") #define pb push_back #define inf 1e9 //std::ios::sync_with_stdio(false); using namespace std; //priority_queue<int,vector<int>,greater<int>> que; get min const double eps = 1.0e-10; const double EPS = 1.0e-4; typedef pair<int, int> pairint; typedef long long ll; typedef unsigned long long ull; //const int maxn = 3e5 + 10; const int turn[4][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}}; //priority_queue<int, vector<int>, less<int>> que; //next_permutation ll Mod = 1000000007; int num[10000]; int cnt; bool check(int a, int b, int c) { if (a + b > c && a + c > b && b + c > a) { return true; } return false; } int main() { int n; int anser = 0; cin >> n; for (int i = 1; i < n; i++) { for (int j = i + 1; j <= n; j++) { int aim = (i ^ j); if (aim >= j && aim <= n && check(i, j, aim)) { //cout << i << " " << j << " " << aim << endl; anser++; } } } cout << anser << endl; return 0; }
C
#include <bits/stdc++.h> #define PI acos(-1.0) #define mem(a,b) memset((a),b,sizeof(a)) #define TS printf("!!! ") #define pb push_back #define inf 1e9 //std::ios::sync_with_stdio(false); using namespace std; //priority_queue<int,vector<int>,greater<int>> que; get min const double eps = 1.0e-10; typedef pair<int, int> pairint; typedef long long ll; typedef unsigned long long ull; //const int maxn = 3e5 + 10; const int maxn = 100005; const int turn[4][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}}; const int turn2[8][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}, {1, -1}, { -1, -1}, {1, 1}, { -1, 1}}; //priority_queue<int, vector<int>, less<int>> que; //next_permutation int main() { //freopen("sample.txt", "w", stdout); ll n, k; cin >> n >> k; if (n == 1 && k <= 2) { cout << "Yes" << endl; return 0; } if (k >= n) { cout << "No" << endl; } else { for (ll i = 1; i <= min(1LL * 50, k); i++) { if (n % i != i - 1) { cout << "No" << endl; return 0; } } cout << "Yes" << endl; } return 0; }
D
奇葩贪心题 假设有两个字符串A B A在B前面的条件是什么?
假设A有SHa个sh BSHb A有Sa个s BSb A有Ha个h BHb 当 SHa+SHb+Sa*Hb>SHa+SHb+Sb*Ha 时成立
转换一下就是A的sh比例比B高的时候 A在B前面
#include <bits/stdc++.h> #define PI acos(-1.0) #define mem(a,b) memset((a),b,sizeof(a)) #define TS printf("!!! ") #define pb push_back #define inf 1e9 //std::ios::sync_with_stdio(false); using namespace std; //priority_queue<int,vector<int>,greater<int>> que; get min const double eps = 1.0e-10; typedef pair<int, int> pairint; typedef long long ll; typedef unsigned long long ull; //const int maxn = 3e5 + 10; const int maxn = 100005; const int turn[4][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}}; const int turn2[8][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}, {1, -1}, { -1, -1}, {1, 1}, { -1, 1}}; //priority_queue<int, vector<int>, less<int>> que; //next_permutation struct node { string str; double per; } s[100005]; bool operator <(node a, node b) { return a.per > b.per; } ll pre[100005]; string aim = ""; int main() { ll anser = 0; //freopen("sample.txt", "w", stdout); int n; cin >> n; for (int i = 1; i <= n; i++) { int now = 0; cin >> s[i].str; int len = s[i].str.size(); for (int j = 0; j < len; j++) { if (s[i].str[j] == 's') { now++; } } if (len - now == 0) { s[i].per = 1000000; } else { s[i].per = (double)now / (double)(len - now); } //cout << s[i].per << endl; } sort(s + 1, s + 1 + n); for (int i = 1; i <= n; i++) { aim += s[i].str; } //cout << aim << endl; int lenth = aim.size(); for (int i = 0; i < lenth; i++) { if (i == 0) { pre[i] = (aim[i] == 's'); } else { pre[i] = pre[i - 1] + (aim[i] == 's'); } if (aim[i] == 'h') { anser += pre[i]; } } cout << anser << endl; return 0; }
E
一般想到的DP思路是DP[i][j]表示前i个用了j块钱能吸引多少鸟 但是这里j太大了(于是题目就提示你C[i]的总值不超过10000)
所以用DP[i][j]表示在前i个吸引了j个鸟最多好剩多少魔力 复杂度: 前面的复杂度是pre[i]较小的时候 后面是pre[i]较大的时候
DP方程:
#include <bits/stdc++.h> #define PI acos(-1.0) #define mem(a,b) memset((a),b,sizeof(a)) #define TS printf("!!! ") #define pb push_back #define inf 1e9 //std::ios::sync_with_stdio(false); using namespace std; //priority_queue<int,vector<int>,greater<int>> que; get min const double eps = 1.0e-10; typedef pair<int, int> pairint; typedef long long ll; typedef unsigned long long ull; //const int maxn = 3e5 + 10; const int maxn = 100005; const int turn[4][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}}; const int turn2[8][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}, {1, -1}, { -1, -1}, {1, 1}, { -1, 1}}; //priority_queue<int, vector<int>, less<int>> que; //next_permutation ll n, W, B, X; ll c[1005]; ll pre[1005]; ll cost[1005]; ll dp[1005][10005]; int main() { //freopen("sample.txt", "w", stdout); // W初始值 B增加的上限 X回复的数目 mem(dp, -1); cin >> n >> W >> B >> X; dp[0][0] = W; for (int i = 1; i <= n; i++) { cin >> c[i]; pre[i] = pre[i - 1] + c[i]; } for (int i = 1; i <= n; i++) { cin >> cost[i]; } for (ll i = 1; i <= n; i++) { for (ll j = 0; j <= pre[i]; j++) { for (ll k = 0; k <= min(j, c[i]); k++) { if (dp[i - 1][j - k] == -1 || 1LL * cost[i]*k > dp[i - 1][j - k]) { continue; } dp[i][j] = max(dp[i][j], dp[i - 1][j - k] - 1LL * k * cost[i]); } if (dp[i][j] != -1) { dp[i][j] = min(dp[i][j] + X, W + 1LL * j * B); } } } for (int i = pre[n]; i >= 0; i--) { if (dp[n][i] >= 0) { cout << i << endl; return 0; } } return 0; }
F
先N*lnN处理出每个数的被除数个数 然后做前缀和 如果K>dp[N] 就无解
所以猜测 当dp[i]>=k时即有解 当数据大于10时 dp数列每两个之间相差不会超过各自之下的i/2+1~i的质数个数(为什么选i/2~i的质数是因为其sum[i]只为1 方便调整)
所以当N>10的时候找到最小的满足dp[i]>=k的i 然后用删去其i/2+1~i之间的质数来调整 dp[i]-k
后来知道 当N<=10的时候 也满足>10的解法 一个数N的被整除数在N^(1/3)数量级 质数则在 N/LogN数量级
#include <bits/stdc++.h> #define PI acos(-1.0) #define mem(a,b) memset((a),b,sizeof(a)) #define TS printf("!!! ") #define pb push_back #define inf 1e9 //std::ios::sync_with_stdio(false); using namespace std; //priority_queue<int,vector<int>,greater<int>> que; get min const double eps = 1.0e-10; const double EPS = 1.0e-4; typedef pair<int, int> pairint; typedef long long ll; typedef unsigned long long ull; //const int maxn = 3e5 + 10; const int turn[4][2] = {{1, 0}, { -1, 0}, {0, 1}, {0, -1}}; //priority_queue<int, vector<int>, less<int>> que; //next_permutation ll Mod = 1000000007; vector<int> prime; int n; ll k; int anserten; ll sum[300005]; ll dp[300005]; int visit[300005]; void dfs(int pos, int x) { if (pos == n + 1) { if (anserten == 0) { int now = 0; for (int i = 1; i <= 5; i++) { if (x & (1 << i)) { for (int j = i * 2; j <= 10; j += i) { if (x & (1 << j)) { //cout << i << " " << j << endl; now++; } } } } if (now == k) { anserten = x; } } return ; } dfs(pos + 1, x + (1 << pos)); dfs(pos + 1, x); } priority_queue<pair<int, int> > que; int main() { cin >> n >> k; for (int i = 1; i <= n; i++) { for (int j = i * 2; j <= n; j += i) { sum[j]++; } } for (int i = 1; i <= n; i++) { dp[i] = dp[i - 1] + sum[i]; } if (k > dp[n]) { cout << "No" << endl; return 0; } else { cout << "Yes" << endl; if (n <= 10) { dfs(1, 0); int anser = 0; for (int i = 1; i <= 10; i++) { if (anserten & (1 << i)) { anser++; } } cout << anser << endl; for (int i = 1; i <= 10; i++) { if (anserten & (1 << i)) { cout << i << " "; } } cout << endl; } else { dp[n + 1] = INT_MAX; int aim; for (aim = 1; aim <= n; aim++) { if (dp[aim] >= k && dp[aim - 1] < k) { break; } } int anser = aim; for (int i = aim; i >= 1; i--) { visit[i] = 1; } for (int i = aim; i >= aim / 2 + 1; i--) { que.push({sum[i], i}); } int cha = dp[aim] - k; pair<int, int> cnt; while (cha > 0) { cnt = que.top(); que.pop(); if (cnt.first <= cha) { cha -= cnt.first; visit[cnt.second] = 0; anser--; } } cout << anser << endl; for (int i = 1; i <= aim; i++) if (visit[i]) { cout << i << " "; } cout << endl; } } return 0; }