CF Round #550 (Div. 3) (A、B、C、D)

A题链接:

http://codeforces.com/contest/1144/problem/A

题意:

给n个字符串,问如果字符串的每一种字符都只出现一次,且出现的字符在字典序必须,即"fced"是符合要求的,“bad"是不合要求的,如果字符串中仅有一个字符也是符合要求的,符合要求输出"Yes”,否则输出"No";

分析:

水题

代码:
#include<bits/stdc++.h>
using namespace std;
constexpr int maxn = 120;
char s[maxn];
int main(){
	int n;
	scanf("%d", &n);
	while(n --){
		set<int> si;
		scanf("%s", s);
		for(int i = 0; s[i]; i += 1) si.insert(s[i]);
		if(*si.rbegin() - *si.begin() + 1 == strlen(s)
			&& si.size() == strlen(s)) puts("Yes");
		else puts("No");
	}
} 
B题链接:

http://codeforces.com/contest/1144/problem/B

题意:

给定n个数,对数组进行删除操作,即删除某个元素,但是删除操作必须以“奇偶奇偶奇偶…”的或者“偶奇偶奇偶奇…”的方式进行,问当不能进行删除操作的时候,所剩下的数的可能的最小值;

分析:

水题

代码:
#include<algorithm>
#include<iostream>
#include<cstring>
#include<string>
#include<cstdio>
#include<vector>
#include<queue>
#include<stack>
#include<cmath>
#include<set>
#include<map>
using namespace std;

const int inf=0x7f7f7f7f;
const int maxn=1e1+50;
const int N=4e5+50;
typedef long long ll;
typedef struct{
    ll u,v,next,w;
}Edge;
Edge e[N];
typedef struct{
    int out,pos;
}Point;
Point p[N];
int cnt,head[N];

inline void add(int u,int v){
    e[cnt].u=u;
    e[cnt].v=v;
    //e[cnt].w=w;
    // e[cnt].f=f;
    e[cnt].next=head[u];
    head[u]=cnt++;
    e[cnt].u=v;
    e[cnt].v=u;
    // e[cnt].w=0;
    // e[cnt].f=-f;
    e[cnt].next=head[v];
    head[v]=cnt++;
}
inline void write(int x)
{
     if(x<0) 
        putchar('-'),x=-x;
     if(x>9)
        write(x/10);
     putchar(x%10+'0');
}
inline int read()
{
    int x = 0;
    int 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;
}

int n,a[2200],b[2200],odd,even;
string s;
int main() {
    cin>>n;
    int x;
    for(int i=1;i<=n;i++){
        cin>>x;
        if(x%2!=0){
            a[odd++]=x;
        }
        else b[even++]=x;
    }
    if(odd==even||odd==even+1||even==odd+1){
        cout<<0<<endl;
        return 0;
    }
    int ans=0;
    if(odd>even){
        sort(a,a+odd);
        for(int i=0;i<odd-even-1;i++){
            ans+=a[i];
        }
    }
    else if(odd<even){
        sort(b,b+even);
        for(int i=0;i<even-odd-1;i++){
            ans+=b[i];
        }
    }
    cout<<ans<<endl;
    return 0;
}
C题链接:

http://codeforces.com/contest/1144/problem/C

题意:

给定一个长度n的整数序列,让你把它分割成两个序列,第一个序列严格递增,第二个序列严格递减,空序列(长度为0)或者只含有一个元素既属于递增序列也属于递减序列,问是否能分割成这样的两个序列,不能输出"NO",否则输出"YES",分别输出递增序列长度,递增序列,递减序列长度,递减序列,空集输出0和空行;

分析:

用set存递增,优先队列存递增序列
对于每个数判断set里是否已经存在,不存在就存进去,若存在则判断有限队列里是否存在,不存在就塞进去,不然输出"NO",退出,最后分别输出就行了;

#include<algorithm>
#include<iostream>
#include<cstring>
#include<string>
#include<cstdio>
#include<vector>
#include<queue>
#include<stack>
#include<cmath>
#include<set>
#include<map>
using namespace std;

const int inf=0x7f7f7f7f;
const int maxn=1e1+50;
const int N=4e5+50;
typedef long long ll;
typedef struct{
    ll u,v,next,w;
}Edge;
Edge e[N];
typedef struct{
    int out,pos;
}Point;
Point p[N];
int cnt,head[N];

inline void add(int u,int v){
    e[cnt].u=u;
    e[cnt].v=v;
    //e[cnt].w=w;
    // e[cnt].f=f;
    e[cnt].next=head[u];
    head[u]=cnt++;
    e[cnt].u=v;
    e[cnt].v=u;
    // e[cnt].w=0;
    // e[cnt].f=-f;
    e[cnt].next=head[v];
    head[v]=cnt++;
}
inline void write(int x)
{
     if(x<0) 
        putchar('-'),x=-x;
     if(x>9)
        write(x/10);
     putchar(x%10+'0');
}
inline int read()
{
    int x = 0;
    int 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;
}

set<int >s;
priority_queue<int>q;
map<int,int>mp;
int t,incr,decr,n;
int main() {
    cin>>n;
    for(int i=0;i<n;i++){
        cin>>t;
        mp[t]++;
        if(mp[t]>2){
            cout<<"NO";
            return 0;
        }
        if(mp[t]==1){
            s.insert(t);
            incr++;
        }
        else if(mp[t]==2){
            q.push(t);
            decr++;
        }
    }
    cout<<"YES"<<endl;
    cout<<incr<<endl;
    set<int >::iterator it=s.begin();
    for(;it!=s.end();it++){
        cout<<*it<<" ";
    }
    cout<<endl;
    cout<<decr<<endl;
    while(!q.empty()){
        int x=q.top();q.pop();
        cout<<x<<" ";
    }
    cout<<endl;
    return 0;
}
D题链接:

http://codeforces.com/contest/1144/problem/D

题意:

给定一个含n个整数的序列,你可以对他进行1. a a a i i i:= a a a i i i+| a a a i i i a a a j j j|;     2. a a a i i i:= a a a i i i-| a a a i i i a a a j j j|;不断的进行这两种操作中的一种,直到这个序列仅有一种元素,输出操作次数,及每次操作的种类(1或2)及 i i i j j j;

分析:

水题;显然的,最终序列里的元素应该是开始序列里数量最多的那种元素,那么就好办了,从这种这种元素开始,往前往后遍历,遇到其他元素就把它变成最多的那种元素,根据大小关系,选择操作种类就行了;

代码:
#include<algorithm>
#include<iostream>
#include<cstring>
#include<string>
#include<cstdio>
#include<vector>
#include<queue>
#include<stack>
#include<cmath>
#include<set>
#include<map>
using namespace std;

const int inf=0x7f7f7f7f;
const int maxn=1e1+50;
const int N=2e5+50;
typedef long long ll;
typedef struct{
    ll u,v,next,w;
}Edge;
Edge e[1];
int cnt,head[1];

inline void add(int u,int v){
    e[cnt].u=u;
    e[cnt].v=v;
    //e[cnt].w=w;
    // e[cnt].f=f;
    e[cnt].next=head[u];
    head[u]=cnt++;
    e[cnt].u=v;
    e[cnt].v=u;
    // e[cnt].w=0;
    // e[cnt].f=-f;
    e[cnt].next=head[v];
    head[v]=cnt++;
}
inline void write(int x)
{
     if(x<0) 
        putchar('-'),x=-x;
     if(x>9)
        write(x/10);
     putchar(x%10+'0');
}

inline int read()
{
    int x = 0;
    int 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;
}

int n,a[N],maxindex,maxcot;
map<int ,int >mp;

int main() {
    cin>>n;
    for(int i=1;i<=n;i++){
        cin>>a[i];
        if(maxcot<++mp[a[i]]){
            maxcot=mp[a[i]];
            maxindex=i;
        }
    }
    cout<<n-maxcot<<endl;
    for(int i=maxindex;i<=n-1;i++){
        if(a[i]<a[i+1]){
            cout<<2<<" "<<i+1<<" "<<i<<endl;
        }
        else 
            cout<<1<<" "<<i+1<<" "<<i<<endl;
        a[i+1]=a[i];
    }
    for(int i=maxindex;i>1;i--){
        if(a[i-1]==a[i])
            continue;
        else if(a[i-1]<a[i])
            cout<<1<<" "<<i-1<<" "<<i<<endl;
        else if(a[i-1]>a[i])
            cout<<2<<" "<<i-1<<" "<<i<<endl;
        a[i-1]=a[i];
    }
    return 0;
}

(仅供个人理解)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值