• 10-20


    比较水的题目吧

    T1:给一个序列,序列中有四种操作,问有多少个非空子序列令一个机器人经过变换后再回到原位

    数据量很小,n^2拿80,另外20只有左右两种命令,求一个类似于前缀和的东西,如果sumi==sumj证明有一种

    #include<bits/stdc++.h>
    using namespace std;
    
    struct hehe{
        int x,y;
    };
    int n,cnt[800100];
    char s[400100];
    
    void work1(){
        hehe a;
        int ans=0;
        for(int i=1;i<=n;++i){
            a.x=0; a.y=0;
            for(int j=i;j<=n;++j){
                if(s[j-1]=='U') a.y++;
                else if(s[j-1]=='D') a.y--;
                else if(s[j-1]=='L') a.x--;
                else if(s[j-1]=='R') a.x++;
                if(!a.x && !a.y) ans++;
            }
        }
        cout<<ans<<endl;
    }
    
    void work2(){
        int x=0,ans=0;
        for(int i=1;i<=n;++i){
            int xx=x;
            if(xx<0) xx=n-xx;
            ans+=cnt[xx];
            cnt[xx]++;
            if(s[i-1]=='L') x++;
            else if(s[i-1]=='R') x--;
        }
        cout<<ans<<endl;
    }
    
    int main(){
        freopen("command.in","r",stdin);
        freopen("command.out","w",stdout);
        
        cin>>n;
        scanf("%s",s);
        if(n<=4000) work1();
        else work2();
        
        fclose(stdin);fclose(stdout);
        return 0;
    }

    T2:将n种颜色涂到n种卡片上,每种卡片有两张,将两张卡片一个正面朝上,一个反面朝上,打乱后将一个正面朝上的和一个反面朝上的放到一张桌子上(总共n张桌子),一个人会用1s的时间打开一个桌子上的反过来的卡片,并且走到另一个正面是这个颜色的桌子,对于Q次询问,求每次ki秒后这个人在哪站着。

    对于30%的数据来说模拟即可,对于100%的数据来说,考虑到一定会出现循环的情况,做一个类似于连通分量的东西,求出每一个块的循环节y,那么问题就是每次询问的ki%y后的数怎么处理了。我的做法是开了一个结构体,存了每个桌子属于第几个块,在这个块中他是第几个,这样排序后就能O(1)的时间解决ki%y后的问题了

    #include<bits/stdc++.h>
    using namespace std;
    
    struct hehe{
        int x,y,dfn;
    }a[100100];
    struct hh{
        int op,id,s,dfn;
    }a1[100100];
    struct haha{
        int id,y;
    }e[100100];
    int n,m,cnt=0,op[100100],kuai[100100],num=0,start[100100];
    
    inline int read(){
        int x=0,f=1;char ch=getchar();
        while(!isdigit(ch)){if(ch=='-') f=-1;ch=getchar();}
        while(isdigit(ch)){x=(x<<3)+(x<<1)+(ch-'0'); ch=getchar();}
        return x*f;
    }
    
    inline void put(int x){
        char ch[30];
        int t=0;
        if(x<0){
            putchar('-');
            x=-x;
        }
        else if(x==0) putchar('0');
        while(x){
            ch[++t]=x%10+'0';
            x/=10;
        }
        while(t) putchar(ch[t--]);
        putchar('
    ');
    }
    
    void work1(){
        int x,y;
        int cnt=0;
        for(int i=1;i<=m;++i){
            x=read(); y=read();
            for(cnt=1;cnt<=y;++cnt){
                x=e[a[x].y].id;
            }
            put(x);
        }
    }
    
    int dfs(int x){
        num++;
        op[x]=cnt;
        a[x].dfn=num;
        a1[x].dfn=num;
        a1[x].op=cnt;
        int Next=e[a[x].y].id;
        if(!op[Next]) dfs(Next);
    }
    
    bool mycmp(hh x,hh y){
        return (x.op<y.op ||x.op==y.op && x.dfn<y.dfn);
    }
    
    void work2(){
        for(int i=1;i<=n;++i){
            if(!op[i]){
                num=0;
                cnt++;
                int x=i;
                while(!op[x]){
                    op[x]=cnt;
                    num++;
                    a[x].dfn=num; a1[x].dfn=num;
                    a1[x].op=cnt;
                    x=e[a[x].y].id;
                }
                kuai[cnt]=num;
            }
        }
        sort(a1+1,a1+n+1,mycmp);
        for(int i=1;i<=n;++i){
            if(a1[i].op==a1[i-1].op) a1[i].s=a1[i].s;
            else{
                a1[i].s=i;
                start[a1[i].op]=i;
            }
        }
        int x,y;
        for(int i=1;i<=m;++i){
            x=read(); y=read();
            y+=a[x].dfn-1;
            int z=op[x];
            y%=kuai[z];
            int s=start[op[x]]+y;
            put(a1[s].id);
        }
    }
    
    int main(){
        freopen("position.in","r",stdin);
        freopen("position.out","w",stdout);
        
        n=read(); m=read();
        int x,y;
        for(int i=1;i<=n;++i){
            x=read(); y=read();
            e[x].y=y; e[x].id=i;
            a[i].x=x; a[i].y=y;
            a1[i].id=i;
        }
        if(n<=20) work1();
        else work2();
        
        fclose(stdin);fclose(stdout);
        return 0;
    }

    T3:给一个图,边权为1,现要求从s1到t1不超过l1,从s2到t2不超过l2,求最多能删除多少边

    求出每两个点之间的距离,然后枚举s1->t1,s2->t2的重叠的边,在剩下的图中尽量选用这些重叠的边,这样就能保证图中删掉的边是最多的

    #include <iostream>
    #include <vector>
    #include <cstring>
    #include <queue>
    using namespace std;
    
    const int MAXN=3010;
    struct hehe{
        int y,next;
    }e[10000];
    int n, m,s1, t1, l1,s2, t2, l2,dis[MAXN][MAXN],lin[MAXN],len=0;
    bool vis[MAXN];
    
    inline void insert(int x,int y){
        e[++len].next=lin[x]; lin[x]=len;
        e[len].y=y;
    }
    
    inline int read(){
        int x=0,f=1;char ch=getchar();
        while(!isdigit(ch)){if(ch=='-') f=-1; ch=getchar();}
        while(isdigit(ch)){x=(x<<3)+(x<<1)+(ch-'0'); ch=getchar();}
        return x*f;
    }
    
    void bfs(){
        for(int i=1;i<=n;i++){
            memset(vis,0,sizeof(vis));
            queue<int>q;
            q.push(i);
            vis[i]=1;
            while(!q.empty()){
                int x=q.front();
                q.pop();
                for(int j=lin[x];j;j=e[j].next){
                    int y=e[j].y;
                    if(!vis[y]){
                        vis[y]=1;
                        dis[i][y]=dis[i][x]+1;
                        q.push(y);
                    }
                }
            }
        }
    }
    
    bool check(int s1, int t1, int s2, int t2, int i, int j){
        return dis[s1][i]+dis[i][j]+dis[j][t1]<=l1 && dis[s2][i]+dis[i][j]+dis[j][t2]<=l2;
    }
    
    int main(){
        freopen("destroy.in","r",stdin);
        freopen("destroy.out","w",stdout);
        n=read(); m=read();
        int x,y;
        for (int i = 1; i <= m; i++){
            x=read(); y=read();
            insert(x,y);
            insert(y,x);
        }
        s1=read(); t1=read(); l1=read();
        s2=read(); t2=read(); l2=read();
        bfs();
        int ans=dis[s1][t1]+dis[s2][t2];
        if(dis[s1][t1]>l1 || dis[s2][t2]>l2){
            cout<<"-1"<<endl;
        }
        else{
            for(int i = 1; i <= n; i++){
                for(int j = 1; j <= n; j++){
                    if(check(s1,t1,s2,t2,i,j)){
                        ans = min(ans,dis[s1][i]+dis[i][j]+dis[j][t1]+dis[s2][i]+dis[j][t2]);
                    }
                    if(check(t1,s1,t2,s2,i,j)){
                        ans = min(ans,dis[t1][i]+dis[i][j]+dis[j][s1]+dis[t2][i]+dis[j][s2]);
                    }
                    if(check(s1,t1,t2,s2,i,j)){
                        ans = min(ans,dis[s1][i]+dis[i][j]+dis[j][t1]+dis[t2][i]+dis[j][s2]);
                    }
                    if(check(t1,s1,s2,t2,i,j)){
                        ans = min(ans,dis[t1][i]+dis[i][j]+dis[j][s1]+dis[s2][i]+dis[j][t2]);
                    }
                }
            }
            cout<<m-ans<<endl;
        }
        return 0;
    }

    T4emmmm

    题目看不懂,题解看不懂,标程看不懂........

  • 相关阅读:
    习惯
    mysql
    mysql
    mysql
    MYSQL
    MYSQL
    mysql
    手动从Spring中获取指定对象
    jdbc连接数据库
    java代码调用exe(cmd命令)
  • 原文地址:https://www.cnblogs.com/assassinyyd/p/7700819.html
Copyright © 2020-2023  润新知