codeforces-1157 (div3)

时间:2019-05-16 00:05:24   收藏:0   阅读:23

赛后经验:疲劳做题不可取。

 

这场状态不好,写的代码质量不高,仅供参考

 

A.map打vis标记,按照题意模拟即可。

WA原因:int变量用%lld输出

技术图片
#include <map>
#include <set>
#include <ctime>
#include <cmath>
#include <queue>
#include <stack>
#include <vector>
#include <string>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <sstream>
#include <iostream>
#include <algorithm>
#include <functional>
using namespace std;
#define For(i, x, y) for(int i=x;i<=y;i++)  
#define _For(i, x, y) for(int i=x;i>=y;i--)
#define Mem(f, x) memset(f,x,sizeof(f))  
#define Sca(x) scanf("%d", &x)
#define Sca2(x,y) scanf("%d%d",&x,&y)
#define Sca3(x,y,z) scanf("%d%d%d",&x,&y,&z)
#define Scl(x) scanf("%lld",&x);  
#define Pri(x) printf("%d\n", x)
#define Prl(x) printf("%lld\n",x);  
#define CLR(u) for(int i=0;i<=N;i++)u[i].clear();
#define LL long long
#define ULL unsigned long long  
#define mp make_pair
#define PII pair<int,int>
#define PIL pair<int,long long>
#define PLL pair<long long,long long>
#define pb push_back
#define fi first
#define se second 
typedef vector<int> VI;
int read(){int x = 0,f = 1;char c = getchar();while (c<0 || c>9){if (c == -) f = -1;c = getchar();}
while (c >= 0&&c <= 9){x = x * 10 + c - 0;c = getchar();}return x*f;}
const double eps = 1e-9;
const int maxn = 110;
const int INF = 0x3f3f3f3f;
const int mod = 1e9 + 7; 
int N,M,K;
map<LL,bool>P,Q;
int main(){
    LL x;
    Scl(x);
    int ans = 0;
    while(1){
        if(!P[x]){
            P[x] = 1;
            ans++;
        }else break;    
        x++;
        while(x && !(x % 10)) x /= 10;    
    }
    Pri(ans);
    return 0;
}
A

 

B.很显然从开头开始能变大就变大,连续一段区间就是从第一个可以变大的数字开头往后面所有能变大就变大的数字,遇到变小就停止

WA原因:没看到连续区间这个条件

技术图片
#include <map>
#include <set>
#include <ctime>
#include <cmath>
#include <queue>
#include <stack>
#include <vector>
#include <string>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <sstream>
#include <iostream>
#include <algorithm>
#include <functional>
using namespace std;
#define For(i, x, y) for(int i=x;i<=y;i++)  
#define _For(i, x, y) for(int i=x;i>=y;i--)
#define Mem(f, x) memset(f,x,sizeof(f))  
#define Sca(x) scanf("%d", &x)
#define Sca2(x,y) scanf("%d%d",&x,&y)
#define Sca3(x,y,z) scanf("%d%d%d",&x,&y,&z)
#define Scl(x) scanf("%lld",&x);  
#define Pri(x) printf("%d\n", x)
#define Prl(x) printf("%lld\n",x);  
#define CLR(u) for(int i=0;i<=N;i++)u[i].clear();
#define LL long long
#define ULL unsigned long long  
#define mp make_pair
#define PII pair<int,int>
#define PIL pair<int,long long>
#define PLL pair<long long,long long>
#define pb push_back
#define fi first
#define se second 
typedef vector<int> VI;
int read(){int x = 0,f = 1;char c = getchar();while (c<0 || c>9){if (c == -) f = -1;c = getchar();}
while (c >= 0&&c <= 9){x = x * 10 + c - 0;c = getchar();}return x*f;}
const double eps = 1e-9;
const int maxn = 2e5 + 10;
const int INF = 0x3f3f3f3f;
const int mod = 1e9 + 7; 
int N,M,K;
char str[maxn];
int to[20];
int main(){
    Sca(N);
    scanf("%s",str + 1);
    for(int i = 1; i <= 9 ; i ++) Sca(to[i]);
    int start = 2;
    for(int i = 1; i <= N ; i ++){
        int id = str[i] - 0;
        if(id < to[id] && start){
            id = to[id];
            start = 1;
        }else if(id > to[id] && start == 1){
            start = 0;
        } 
        printf("%d",id);
    }
    return 0;
}
View Code

 

C1,C2.

贪心做法,不断往两端取较小的那一个,遇到一样的就会发现如果取左边之后就只能从左边取,反之只能从右边取。

比较一下哪个大就可以了

技术图片
#include <map>
#include <set>
#include <ctime>
#include <cmath>
#include <queue>
#include <stack>
#include <vector>
#include <string>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <sstream>
#include <iostream>
#include <algorithm>
#include <functional>
using namespace std;
#define For(i, x, y) for(int i=x;i<=y;i++)  
#define _For(i, x, y) for(int i=x;i>=y;i--)
#define Mem(f, x) memset(f,x,sizeof(f))  
#define Sca(x) scanf("%d", &x)
#define Sca2(x,y) scanf("%d%d",&x,&y)
#define Sca3(x,y,z) scanf("%d%d%d",&x,&y,&z)
#define Scl(x) scanf("%lld",&x);  
#define Pri(x) printf("%d\n", x)
#define Prl(x) printf("%lld\n",x);  
#define CLR(u) for(int i=0;i<=N;i++)u[i].clear();
#define LL long long
#define ULL unsigned long long  
#define mp make_pair
#define PII pair<int,int>
#define PIL pair<int,long long>
#define PLL pair<long long,long long>
#define pb push_back
#define fi first
#define se second 
typedef vector<int> VI;
int read(){int x = 0,f = 1;char c = getchar();while (c<0 || c>9){if (c == -) f = -1;c = getchar();}
while (c >= 0&&c <= 9){x = x * 10 + c - 0;c = getchar();}return x*f;}
const double eps = 1e-9;
const int maxn = 4e5 + 10;
const int INF = 0x3f3f3f3f;
const int mod = 1e9 + 7; 
int N,M,K;
int a[maxn];
string s;
int main(){
    Sca(N);
    for(int i = 1; i <= N ; i ++) Sca(a[i]);
    int l = 1,r = N;
    int ans = 0;
    int MIN = 0;
    while(1){
        if(l > r || (a[l] <= MIN && a[r] <= MIN)) break;
        if((a[l] > MIN && a[l] < a[r]) || a[r] <= MIN){
            ans++;
            MIN = a[l];
            l++;
            s.pb(L);
        }else if(a[r] > MIN && a[l] != a[r]){
            ans++;
            MIN = a[r];
            r--;
            s.pb(R);
        }else if(a[l] == a[r]){
            int L = l,R = r;
            int tmp1 = 0,tmp2 = 0;
            int p = MIN;
            while(L <= r && a[L] > p){
                tmp1++;
                p = a[L];
                L++;
            }
            p = MIN;
            while(l <= R && a[R] > p){
                tmp2++;
                p = a[R];
                R--;
            }
            ans += max(tmp1,tmp2);
            if(tmp1 > tmp2){
                while(tmp1--) s.pb(L);
            }else{
                while(tmp2--) s.pb(R);
            }
            break;
        }
    }
    Pri(ans);
    cout << s << endl;
    return 0;
}
C

 

D.首先排除掉题目过少天数过多的情况,也就是K < N * ( N + 1 ) / 2必定为NO

其次构造一个N天,一开始数目为1,2,3,4...N

然后给他们全部加上一个数字K / N,就会发现必定也符合题意,剩余的就从后面开始往前面填充就可以了。

WA原因:忘记输出YES了

技术图片