码迷,mamicode.com
首页 > 其他好文 > 详细

10/10

时间:2019-10-09 19:41:15      阅读:95      评论:0      收藏:0      [点我收藏+]

标签:两种   ide   include   main   i++   down   nod   字符串   直接   

A:

题意:给一个大小为n的数组A,让你把A分成若干个(1 or more)新的数组,使得新数组的和不为0;

解:NO的情况只有 数组内所有元素都为0

  YES的情况:1.数组A的所有元素和不为0:直接输出(1,n);

        2.数组A的所有元素和为0:必定存在sum(1,i)!=0,sum(i+1,n)!=0;//(sum(1,i)表示元素下标和(1-i))

技术图片
#include <bits/stdc++.h>
using namespace std;
const int MAXN=1e5+10;
int a[MAXN];
 
int main(){
    int n;
    cin>>n;
    int sum=0;
    for(int i=1;i<=n;i++){
        cin>>a[i];
        sum+=a[i];
    }
    if(sum){
        cout<<"YES"<<endl;
        cout<<1<<endl;
        cout<<1<< <<n<<endl;
    }
    else{
        int flag=0;
        for(int i=1;i<=n;i++){
            sum+=a[i];
            if(sum){
                flag=1;
                cout<<"YES"<<endl;
                cout<<2<<endl;
                cout<<1<< <<i<<endl;
                cout<<i+1<< <<n<<endl;
                break;
            }
        }
        if(!flag)cout<<"NO"<<endl;
 
    }
 
 
 
 
    return 0;
}
View Code

B:

题意:4*4的棋盘,是否存在放一个棋‘x‘,使得存在三个连续的‘x‘,(横竖斜)

解:暴力每个可能的位置,只有4*4;

技术图片
#include <bits/stdc++.h>
using namespace std;
const int MAXN=1e5+10;
char s[10][10];
int a[10][10];
int main(){
    for(int i=1;i<=4;i++){
        scanf("%s",s[i]+1);
    }
    for(int i=1;i<=4;i++){
        for(int j=1;j<=4;j++){
            if(s[i][j]==x){
                a[i][j]=1;
            }
            else if(s[i][j]==o){
                a[i][j]=-1;
            }
            else a[i][j]=0;
        }
    }
    int flag=0;
    for(int i=1;i<=4;i++){
        for(int j=1;j<=2;j++){
            if(a[i][j]+a[i][j+1]+a[i][j+2]>=2){
                flag=1;
            }
            if(a[j][i]+a[j+1][i]+a[j+2][i]>=2){
                flag=1;
            }
        }
    }
    for(int i=1;i<=4;i++){
        for(int j=1;j<=4;j++){
            if(i<=2&&j<=2){
                if(a[i][j]+a[i+1][j+1]+a[i+2][j+2]>=2){
                    flag=1;
                }
            }
            else if(i<=2&&j>2){
                if(a[i][j]+a[i+1][j-1]+a[i+2][j-2]>=2){
                    flag=1;
                }
            }
        }
    }
    if(flag)cout<<"YES"<<endl;
    else cout<<"NO"<<endl;
 
 
 
 
    return 0;
}
View Code

C:

题意:给一个n的数组A,从数组A中找出一个可重复集合,集合满足所有元素的gcd不为1,输出最大 集合的个数

解:统计因子,将所有元素的因子进行统计,答案就是所有因子最大的个数,因为si<=1e5,因子也不会太大;

技术图片
#include <bits/stdc++.h>
using namespace std;
const int MAXN=1e5+10;
int num[MAXN];
int a[MAXN];
void gao(int x){
    for(int i=2;i<=sqrt(x);i++){
        if(x%i==0){
            if(i*i!=x){
                num[i]++;num[x/i]++;
            }
            else num[i]++;
        }
    }
    num[x]++;
}
int main(){
    ios::sync_with_stdio(false);
    int n;
    cin>>n;
    for(int i=1;i<=n;i++){
        cin>>a[i];
        gao(a[i]);
    }
    int ans=1;
    for(int i=2;i<=MAXN-5;i++){
        ans=max(ans,num[i]);
    }
    cout<<ans<<endl;
 
 
 
 
    return 0;
}
View Code

D:

题意:给一个字符串,‘!‘可以换为其他字母,满足整个字符串自循环,按题目顺序输出‘!‘换为其他字母的个数

解:模拟~用map瞎模拟过去;

技术图片
#include <bits/stdc++.h>
using namespace std;
const int MAXN=1e5+10;
char s[MAXN];
int a[5];
int num[5];
bool vis[5];
map<char,int>mp;
int main(){
    ios::sync_with_stdio(false);
    mp[R]=1;mp[B]=2;mp[Y]=3;mp[G]=4;mp[!]=0;
    scanf("%s",s);
    for(int i=0;i<strlen(s);i++){
        if(s[i]!=!)
        a[i%4]=mp[s[i]];
        else num[i%4]++;
    }
 
    for(int i=0;i<4;i++){
        vis[a[i]]=true;
    }
    for(int i=0;i<4;i++){
        if(a[i]==0){
            for(int j=1;j<=4;j++){
                if(!vis[j]){
                    a[i]=j;
                    vis[j]=true;
                    break;
                }
            }
        }
    }
 
    for(int i=1;i<=4;i++){
        for(int j=0;j<4;j++){
            if(a[j]==i){
                cout<<num[j]<< ;
            }
        }
    }
    cout<<endl;
 
 
 
 
    return 0;
}
View Code

E:

解:线段树,字母用二进制存,每个结点存两个子节点的或值;

最后查询的时候二进制有几个1就是有几个不同的字母;(可以自行思考一下)

技术图片
#include <bits/stdc++.h>
using namespace std;
const int MAXN=1e5+10;
int tree[MAXN*4];
int tot=0;
char s[MAXN];
char t[5];
int n;
void build(int root,int l,int r){
    if(l==r){
        tree[root]=1<<(s[l]-a);
        return ;
    }
    int mid=(l+r)>>1;
    build(root<<1,l,mid);
    build(root<<1|1,mid+1,r);
    tree[root]=tree[root<<1]|tree[root<<1|1];
}
void gao(int root,int l,int r,int p,char x){
    if(l==r){
        int w=1<<(x-a);
        tree[root]=w;
        return ;
    }
    int mid=(l+r)>>1;
    if(p<=mid)gao(root<<1,l,mid,p,x);
    else gao(root<<1|1,mid+1,r,p,x);
    tree[root]=tree[root<<1]|tree[root<<1|1];
}
int query(int root,int l,int r,int L,int R){
    if(L>r||R<l)return 0;
    if(l>=L&&R>=r)return tree[root];
    int mid=(l+r)>>1;
    int res=0;
    res|=query(root<<1,l,mid,L,R);
    res|=query(root<<1|1,mid+1,r,L,R);
    return res;
 
}
int main(){
    scanf("%s",s+1);
    n=strlen(s+1);
    build(1,1,n);
    int T;
    scanf("%d",&T);
    while(T--){
        int o;
        scanf("%d",&o);
        if(o==1){
            int p;
            scanf("%d%s",&p,t);
            //cout<<p<<" "<<t[0]<<endl;
            gao(1,1,n,p,t[0]);
        }
        else {
            int l,r;
            scanf("%d%d",&l,&r);
            int res=query(1,1,n,l,r);
            int ans=0;
            while(res){
                if(res&1)ans++;
                res>>=1;
            }
            printf("%d\n",ans);
        }
    }
 
 
 
    return 0;
}
View Code

F:

题意:水从(0,0)进,判断能否从(1,n)出;

解:虽然有6种管道,但是可以旋转,所以就可以看成两种管道;

dfs(x,y,last):x,y为当前位置,last表示从哪里留过来的;(写了大半个小时,改来改去,可能我写的有点繁琐,也懒得改了)

技术图片
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int MAXN=2e5+10;
int a[5][MAXN];
bool vis[5][MAXN];
string s;
int n;//last  up 1 down 2 left 3
bool dfs(int x,int y,int last){
    //cout<<"x="<<x<<‘ ‘<<"y="<<y<<"last="<<last<<endl;
    if(!vis[x][y])return false;
    if(y==(n+1)&&x==2)return true;
    if(y>=(n+1))return false;
    if(x<1||x>2)return false;
    if(a[x][y]){
        if(last==1||last==2){
            vis[x][y+1]=true;
            if(dfs(x,y+1,3))return true;
            else vis[x][y+1]=false;
        }
        else if(last==3){
            if(x==1){
                vis[x+1][y]=true;
                if(dfs(x+1,y,1))return true;
                else vis[x+1][y]=false;
            }
            else {
                vis[x-1][y]=true;
                if(dfs(x-1,y,2))return true;
                else vis[x-1][y]=false;
            }
        }
    }
    else {
        if(last==3){
            vis[x][y+1]=true;
            if(dfs(x,y+1,3))return true;
            else vis[x][y+1]=false;
        }
    }
    return false;
}
int main(){
    ios::sync_with_stdio(false);
    int T;
    cin>>T;
    while(T--){
        cin>>n;
        for(int i=1;i<=2;i++){
            cin>>s;
            for(int j=0;j<n;j++){
                if((s[j]-0)<=2)a[i][j+1]=0;
                else a[i][j+1]=1;
                vis[i][j+1]=false;
            }
        }
        vis[1][n+1]=vis[2][n+1]=false;
        vis[1][1]=true;
        if(dfs(1,1,3)){
            cout<<"YES"<<endl;
        }
        else cout<<"NO"<<endl;
    }
 
 
 
 
    return 0;
}
View Code

G:

题意:给n个区间,问是否存在一个区间,使得重叠k次,求最大的区间;

解:按区间的左端点排序,然后维护一个大小为k的按照右端点从小到大的队列。并且不断更新最小的right值。(新进来的right一定大于队首的right值),那么每个时刻的长度都是队首的right值 减去新进来的left值,不断更新结果。另外注意输出。

技术图片
#include <bits/stdc++.h>
using namespace std;
const int MAXN=3e5+10;
int n,k;
struct node{
    int l,r,id;
}a[MAXN];
bool cmp(node x,node y){
    return x.l==y.l?x.r<y.r:x.l<y.l;
}
priority_queue<int,vector<int>,greater<int> >que;
int main(){
    ios::sync_with_stdio(false);
    cin>>n>>k;
    for(int i=1;i<=n;i++){
        cin>>a[i].l>>a[i].r;
        a[i].id=i;
    }
    sort(a+1,a+1+n,cmp);
    /*for(int i=1;i<=n;i++){
        cout<<a[i].l<<‘ ‘<<a[i].r<<‘ ‘<<a[i].id<<endl;
    }*/
    int ans=0;
    int L=a[1].l;
    for(int i=1;i<=n;i++){
        que.push(a[i].r);
        if(que.size()>k)que.pop();
        int res=que.top()-a[i].l+1;
        if(ans<res&&que.size()==k){
            ans=res;
            L=a[i].l;
        }
    }
    cout<<ans<<endl;
    if(ans){
        for(int i=1;i<=n;i++){
            if(a[i].l<=L&&a[i].r>=L+ans-1){
                cout<<a[i].id<< ;
                k--;
            }
            if(!k)break;
        }
        cout<<endl;
    }
    else{
        for(int i=1;i<=k;i++){
            cout<<i<< ;
        }
        cout<<endl;
    }
 
 
 
 
    return 0;
}
View Code

 

10/10

标签:两种   ide   include   main   i++   down   nod   字符串   直接   

原文地址:https://www.cnblogs.com/lin1874/p/11643484.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!