zoukankan      html  css  js  c++  java
  • 洛谷 P2790 ccj与zrz之积木问题

    题目背景

    ccj和zrz无聊到了玩起了搭积木...(本题选自uva101,翻译来自《算法竞赛入门经典2》)

    题目描述

    从左到右有n个木块,编号从0到n-1,要求模拟以下4种操作(下面的a和B都是木块编号,归为表示比如1号木块归到1号位去)。

    move a onto b 把a和b上方的木块全部归位,然后把a摞在b上面。

    move a over b 把a上方的全部归位,然后把a放在b所在木块堆的顶部。

    pile a onto b 把b上方的木块全部归位,然后把a及上面的木块整体摞在b上面

    pile a over b 把a及上面的木块整体摞在b所在木块堆的顶部。

    遇到quit停止。a和b在同一堆的指令时非法指令,应当忽略。

    最后输出每个位置的木块列表,按照从底部到顶部的顺序排列。

    输入输出格式

    输入格式:

     

    第一行:n。

    接下来若干行:每行一个指令(语法不会错),遇到quit停止。

     

    输出格式:

     

    n行,第i行输出一个i和冒号,然后一个空格,输出,它位置上的所有积木。

     

    输入输出样例

    输入样例#1: 复制
    10
    move 9 onto 1
    move 8 over 1
    move 7 over 1
    move 6 over 1
    pile 8 over 6
    pile 8 over 5
    move 2 over 1
    move 4 over 9
    quit
    输出样例#1: 复制
    0: 0
    1: 1 9 2 4
    2:
    3: 3
    4:
    5: 5 8 7 6
    6:
    7:
    8:
    9:

    说明

    0 < n < 25。

     思路:模拟

    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    int n,a,b;
    int id[30];
    char s[3][5];
    struct nond{
        int num[30],top;
    }v[30];
    void work1(){
        int pos=id[a];
        for(int i=v[pos].top;i>=1;i--)
            if(v[pos].num[v[pos].top]!=a){
                v[v[pos].num[v[pos].top]].top++;
                id[v[id[a]].num[v[id[a]].top]]=v[id[a]].num[v[id[a]].top];
                v[v[pos].num[v[pos].top]].num[v[v[pos].num[v[pos].top]].top]=v[pos].num[v[pos].top];
                v[id[a]].top--;
            }
            else{
                v[id[a]].top--;v[id[b]].top++;
                v[id[b]].num[v[id[b]].top]=a;
                id[a]=id[b];
                break;
            }
    }
    void work2(){
        for(int i=v[id[a]].top;i>=1;i--)
            if(v[id[a]].num[v[id[a]].top]!=a){
                v[v[id[a]].num[v[id[a]].top]].top++;
                id[v[id[a]].num[v[id[a]].top]]=v[id[a]].num[v[id[a]].top];
                v[v[id[a]].num[v[id[a]].top]].num[v[v[id[a]].num[v[id[a]].top]].top]=v[id[a]].num[v[id[a]].top];
                v[id[a]].top--;
            }
        for(int i=v[id[b]].top;i>=1;i--)
            if(v[id[b]].num[v[id[b]].top]!=b){
                v[v[id[b]].num[v[id[b]].top]].top++;
                id[v[id[b]].num[v[id[b]].top]]=v[id[b]].num[v[id[b]].top];
                v[v[id[b]].num[v[id[b]].top]].num[v[v[id[b]].num[v[id[b]].top]].top]=v[id[b]].num[v[id[b]].top];
                v[id[b]].top--;
            }
        v[id[a]].top--;v[id[b]].top++;
        v[id[b]].num[v[id[b]].top]=a;
        id[a]=id[b];
    }
    void work3(){
        for(int i=v[id[b]].top;i>=1;i--)
            if(v[id[b]].num[v[id[b]].top]!=b){
                v[v[id[b]].num[v[id[b]].top]].top++;
                id[v[id[b]].num[v[id[b]].top]]=v[id[b]].num[v[id[b]].top];
                v[v[id[b]].num[v[id[b]].top]].num[v[v[id[b]].num[v[id[b]].top]].top]=v[id[b]].num[v[id[b]].top];
                v[id[b]].top--;
            }
        int pos=id[a];
        for(int i=v[pos].top;i>=1;i--)
            if(v[pos].num[i]==a){
                for(int j=i;j<=v[pos].top;j++){
                    v[id[b]].top++;
                    v[id[b]].num[v[id[b]].top]=v[pos].num[j];
                    id[v[pos].num[j]]=id[b];
                }
                v[pos].top-=i;
                break;
            }
    }
    void work4(){
        int pos=id[a];
        for(int i=v[pos].top;i>=1;i--)
            if(v[pos].num[i]==a){
                for(int j=i;j<=v[pos].top;j++){
                    v[id[b]].top++;
                    v[id[b]].num[v[id[b]].top]=v[pos].num[j];
                    id[v[pos].num[j]]=id[b];
                }
                v[pos].top-=i;
                break;
            }
    }
    int main(){
        scanf("%d",&n);
        for(int i=0;i<n;i++)    v[i].num[1]=i,v[i].top=1,id[i]=i;
        for(int i=1;i<=n;i++){
            cin>>s[1];
            if(s[1][0]=='m'){
                scanf("%d",&a);
                scanf("%s %d",s[2],&b);
                if(id[a]==id[b])    continue;
                if(s[2][1]=='v')    work1();
                else work2();
            }
            else if(s[1][0]=='p'){
                scanf("%d",&a);
                scanf("%s %d",s[2],&b);
                if(id[a]==id[b])    continue;
                if(s[2][1]=='n')    work3();
                else work4();
            }
            else    break;
        }
        for(int i=0;i<n;i++){
            cout<<i<<": ";
            for(int j=1;j<=v[i].top;j++)
                cout<<v[i].num[j]<<" ";
            cout<<endl;
        }
    }
    调不出来的40分gg

    思路:用vector维护。

    #include<vector>
    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    int n,a,b;
    int h1,q1,h2,q2;
    char p[10],q[10];
    vector<int>s[32];
    void find(){
        for(int i=0;i<n;i++)
        for(int o=0;o<s[i].size();o++){
            if(s[i][o]==a){ h1=i;q1=o; }
            if(s[i][o]==b){ h2=i;q2=o; }
        }
    }
    void moveonto(){
        for(int i=q1+1;i<s[h1].size();i++)
               s[s[h1][i]].push_back(s[h1][i]);
        for(int i=q2+1;i<s[h2].size();i++)
            s[s[h2][i]].push_back(s[h2][i]);
        s[h1].resize(q1);
        s[h2].resize(q2+1);
        s[h2].push_back(a);
    }
    void moveover(){
        for(int i=q1+1;i<s[h1].size();i++)
            s[s[h1][i]].push_back(s[h1][i]);
        s[h1].resize(q1);
        s[h2].push_back(a);
    }
    void pileonto(){
        for(int i=q2+1;i<s[h2].size();i++)
            s[s[h2][i]].push_back(s[h2][i]);
        s[h2].resize(q2+1);
        for(int i=q1;i<s[h1].size();i++)
            s[h2].push_back(s[h1][i]);
        s[h1].resize(q1);
    }
    void pileover(){
        for(int i=q1;i<s[h1].size();i++)
            s[h2].push_back(s[h1][i]);
        s[h1].resize(q1);
    }
    int main(){
        scanf("%d",&n);
        for(int i=0;i<n;i++)    s[i].push_back(i);
        while(1){
            scanf("%s",p);
            if(strcmp(p,"quit")==0)    break;
            scanf("%d%s%d",&a,q,&b);
            find();
            if(h1==h2)    continue;
            if(strcmp(p,"move")==0&&strcmp(q,"onto")==0)    moveonto();
            if(strcmp(p,"move")==0&&strcmp(q,"over")==0)    moveover();
            if(strcmp(p,"pile")==0&&strcmp(q,"onto")==0)    pileonto();
            if(strcmp(p,"pile")==0&&strcmp(q,"over")==0)    pileover();
        }
        for(int i=0;i<n;i++){
            printf("%d:",i);
            for(int o=0;o<s[i].size();o++)
                printf(" %d",s[i][o]);
            printf("
    ");
        }
    }
    细雨斜风作晓寒。淡烟疏柳媚晴滩。入淮清洛渐漫漫。 雪沫乳花浮午盏,蓼茸蒿笋试春盘。人间有味是清欢。
  • 相关阅读:
    [NOIP-P1125]逃亡的准备
    [NOIP-P1125]两个数差
    问题 B: [NOIP-P1125]飙车
    [NOIP-P1125]计算概率
    牛跳
    化学方程式
    c++第十七章-(内联函数)
    c++第十六章-(函数模板与类模板)
    《将博客搬至CSDN》
    cocoaPods安装与使用
  • 原文地址:https://www.cnblogs.com/cangT-Tlan/p/7881427.html
Copyright © 2011-2022 走看看