1. 程式人生 > >CodeForces Round #498 div3

CodeForces Round #498 div3

命令 col 對稱 stdout add 完全 最大的 其他 const

A:

題目沒讀, 啥也不會的室友幫我寫的。

技術分享圖片
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
 4 #define LL long long
 5 #define ULL unsigned LL
 6 #define fi first
 7 #define se second
 8 #define pb push_back
 9 #define lson l,m,rt<<1
10
#define rson m+1,r,rt<<1|1 11 #define max3(a,b,c) max(a,max(b,c)) 12 #define min3(a,b,c) min(a,min(b,c)) 13 typedef pair<int,int> pll; 14 const int INF = 0x3f3f3f3f; 15 const LL mod = 1e9+7; 16 const int N = 1e5+10; 17 18 int main(){ 19 ///Fopen; 20 int a; 21 cin>>a; 22 int
b[a]; 23 for(int i=0;i<a;i++){ 24 cin>>b[i]; 25 } 26 for(int i=0;i<a;i++){ 27 if(b[i]%2==0) b[i]=b[i]-1; 28 } 29 for(int i=0;i<a;i++){ 30 cout<<b[i]<< ; 31 } 32 return 0; 33 }
A

B:

題意:一共有n個任務,m天內完成,每個任務必須都要完成,並且不能重復完成,還要按順序完成,每天能獲得的利潤為當天任務最大的那個利潤,現在劃分每天完成的任務數量, 來獲得最大的總利潤。

題解:選出利潤最大的m個任務, 然後每天都包含其中一個就好了。

技術分享圖片
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
 4 #define LL long long
 5 #define ULL unsigned LL
 6 #define fi first
 7 #define se second
 8 #define pb push_back
 9 #define lson l,m,rt<<1
10 #define rson m+1,r,rt<<1|1
11 #define max3(a,b,c) max(a,max(b,c))
12 #define min3(a,b,c) min(a,min(b,c))
13 typedef pair<int,int> pll;
14 const int INF = 0x3f3f3f3f;
15 const LL mod = 1e9+7;
16 const int N = 1e5+10;
17 pll p[N];
18 int vis[N];
19 int main(){
20     ///Fopen;
21     int n, m;
22     scanf("%d%d", &n, &m);
23     for(int i = 1; i <= n; i++){
24         scanf("%d", &p[i].fi);
25         p[i].se = i;
26     }
27     sort(p+1, p+1+n);
28     int ans = 0;
29     for(int i = n; i >= n - m + 1; i--){
30         ans += p[i].fi;
31         vis[p[i].se] = 1;
32     }
33     printf("%d\n", ans);
34     int cnt = 0;
35     for(int i = 1; i <= n; i++){
36         cnt++;
37         if(vis[i]){
38             m--;
39             if(m == 0) cnt += (n-i);
40             printf("%d ", cnt);
41             cnt = 0;
42         }
43     }
44     return 0;
45 }
B

C:

題意:給你一堆數列,現在將他們分成連續的3堆,可以為空,現在要求第一堆和最後一堆相等的情況下,最大的第一堆值是多少。

題解:左右開始選,左邊大了就右邊加上一個新的數,右邊大了就左邊加上一個新的數,每次相等就記錄答案。

技術分享圖片
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
 4 #define LL long long
 5 #define ULL unsigned LL
 6 #define fi first
 7 #define se second
 8 #define pb push_back
 9 #define lson l,m,rt<<1
10 #define rson m+1,r,rt<<1|1
11 #define max3(a,b,c) max(a,max(b,c))
12 #define min3(a,b,c) min(a,min(b,c))
13 typedef pair<int,int> pll;
14 const int INF = 0x3f3f3f3f;
15 const LL mod = 1e9+7;
16 const int N = 2e5+10;
17 LL d[N];
18 int main(){
19     ///Fopen;
20     int n;
21     scanf("%d", &n);
22     for(int i = 1; i <= n; i++)
23         scanf("%I64d", &d[i]);
24     LL sum1 = 0, sum3 = 0;
25     int i = 1, j = n;
26     sum1 = d[1];
27     sum3 = d[n];
28     LL ans = 0;
29     while(i < j){
30         if(sum1 == sum3){
31             ans = sum1;
32             sum1 += d[++i];
33         }
34         else if(sum1 < sum3) sum1 += d[++i];
35         else if(sum1 > sum3) sum3 += d[--j];
36 
37     }
38     cout << ans << endl;
39     return 0;
40 }
C

D:

題意:給你2個等長的字符串A B,現在可以對於A B串裏面的交換對稱位置的字符,也可以交換AB同一位置的字符, 然後對於A串還有一個魔法操作就是選擇一個位置上的字符,將這個字符改變成其他任意一個字符。現在求先交換字符位置後,要使得這2個串完全相等需要的魔法操作數是多少。

題解:我們可以發現,對於一個位置來說有其他3個位置是對應的,那麽我們從前面往後面掃, 如果這一個位置的AB上的字符都對到了, 那麽我們就不對這個位置上的字符進行處理, 然後如果不對, 我們看一下A的對稱位置上的字符是不是能和B匹配, 如果可以就將A的2個字符交換, 如果不行我們再看看B的對稱位置上的字符是不是和改位置上的字符相等, 如果是, 那麽交換該位置的A 和 對稱位置上的B。

最後我們再看看AB串相同的位置有多少個字符不相等, 就是答案了。

技術分享圖片
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
 4 #define LL long long
 5 #define ULL unsigned LL
 6 #define fi first
 7 #define se second
 8 #define pb push_back
 9 #define lson l,m,rt<<1
10 #define rson m+1,r,rt<<1|1
11 #define max3(a,b,c) max(a,max(b,c))
12 #define min3(a,b,c) min(a,min(b,c))
13 typedef pair<int,int> pll;
14 const int INF = 0x3f3f3f3f;
15 const LL mod = 1e9+7;
16 const int N = 1e5+10;
17 char a[N], b[N];
18 int main(){
19     ///Fopen;
20     int n;
21     scanf("%d", &n);
22     scanf("%s", a+1);
23     scanf("%s", b+1);
24     for(int i = 1; i <= n; i++){
25         if(a[i] == b[i]) continue;
26         int j = n - i + 1;
27         if(a[j] == b[i]) swap(a[j], a[i]);
28         if(b[j] == b[i]) swap(a[i], b[j]);
29     }
30     int ans = 0;
31     for(int i = 1; i <= n; i++){
32         ans += (a[i] != b[i]);
33     }
34     cout << ans << endl;
35     return 0;
36 }
D

看了一眼好友列表裏面的代碼, 就我的最簡單了, 233。

E:

題意:一個公司裏面有n個員工, 1號員工為Boss, 然後其他n-1個人都有一個直接上級, 然後上級的上級也算上級, 然後每次一個人接到任務, 都會將任務傳遞給所有下級, 現在有q次詢問,輸入一個u k

要求輸出第u個員工收到命令後, 第k個收到命令的員工的編號是多少, 如果沒有第k個收到命令的員工就輸出-1。

題解:dfs序,記錄一下開始的dfs序和結束的dfs序, 然後每次詢問的時候, 判斷一下,有沒有第k個員工, 如果有用dfs序輸出那個員工的編號就是答案了。

註意的就是鏈式前向星是倒著遍歷邊的, 所以如果使用鏈式前向星要換一個順序建邊。

技術分享圖片
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
 4 #define LL long long
 5 #define ULL unsigned LL
 6 #define fi first
 7 #define se second
 8 #define pb push_back
 9 #define lson l,m,rt<<1
10 #define rson m+1,r,rt<<1|1
11 #define max3(a,b,c) max(a,max(b,c))
12 #define min3(a,b,c) min(a,min(b,c))
13 typedef pair<int,int> pll;
14 const int INF = 0x3f3f3f3f;
15 const LL mod = 1e9+7;
16 const int N = 2e5+10;
17 int in[N], out[N];
18 vector<int> son[N];
19 int ans[N];
20 int tot = 0;
21 void dfs(int u){
22     ans[++tot] = u;
23     in[u] = tot;
24     for(int i = 0; i < son[u].size(); i++)
25         dfs(son[u][i]);
26     out[u] = tot;
27 }
28 int main(){
29     ///Fopen;
30     int n, m, u;
31     scanf("%d%d", &n, &m);
32     for(int i = 2; i <= n; i++){
33         scanf("%d", &u);
34         son[u].pb(i);
35     }
36     dfs(1);
37     int v, k;
38     while(m--){
39         scanf("%d%d", &v, &k);
40         if(out[v] < in[v] + k - 1)
41             printf("-1\n");
42         else{
43             printf("%d\n", ans[in[v]+k-1]);
44         }
45     }
46     return 0;
47 }
E

F:

題意:從[1,1] 走到 [n, m] 的位置, 只能朝右和朝下走, 將路過的值都 xor 起來, 最後求到達[n, m]的時候 xor 的值為k的方案數是多少。

題解:如果直接走到n,m的狀態數太多, 所以我們將步數對半分, 從[1,1]開始走一半的步數, 從[n,m]開始走剩下的步數, 然後停下來的時候再統計答案。

技術分享圖片
 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define Fopen freopen("_in.txt","r",stdin); freopen("_out.txt","w",stdout);
 4 #define LL long long
 5 #define ULL unsigned LL
 6 #define fi first
 7 #define se second
 8 #define pb push_back
 9 #define lson l,m,rt<<1
10 #define rson m+1,r,rt<<1|1
11 #define max3(a,b,c) max(a,max(b,c))
12 #define min3(a,b,c) min(a,min(b,c))
13 typedef pair<int,int> pll;
14 const int inf = 0x3f3f3f3f;
15 const LL INF = 0x3f3f3f3f3f3f3f3f;
16 const LL mod =  (int)1e9+7;
17 const int N = 25;
18 map<LL, int> mp[N][N];
19 LL a[N][N];
20 int n, m;
21 LL k;
22 void dfs1(int x, int y, int t, LL now){
23     if(t == 0){
24         mp[x][y][now]++;
25         return ;
26     }
27     if(x+1 <= n) dfs1(x+1,y,t-1,now^a[x][y]);
28     if(y+1 <= m) dfs1(x, y+1, t-1, now^a[x][y]);
29 }
30 LL ans = 0;
31 void dfs2(int x, int y, int t, LL now){
32     if(t == 0){
33         ans += mp[x][y][now];
34         return ;
35     }
36     if(x-1) dfs2(x-1,y,t-1,now^a[x-1][y]);
37     if(y-1) dfs2(x,y-1,t-1,now^a[x][y-1]);
38 }
39 int main(){
40     scanf("%d%d%I64d", &n, &m, &k);
41     for(int i = 1; i <= n; i++)
42         for(int j = 1; j <= m; j++)
43             scanf("%I64d", &a[i][j]);
44     int t = n + m - 2;
45     dfs1(1,1,t/2,0);
46     dfs2(n,m,t-t/2,k^a[n][m]);
47     cout << ans << endl;
48     return 0;
49 }
F

CodeForces Round #498 div3