zoukankan      html  css  js  c++  java
  • [蓝桥杯][2014年第五届真题]套娃

    时间限制: 1Sec 内存限制: 128MB 提交: 5 解决: 0

    题目描述

        作为 drd 送的生日礼物,atm 最近得到了一个俄罗斯娃娃。他对这个俄罗斯娃娃的构造很感兴趣。

        俄罗斯娃娃是一层一层套起来的。假设:一个大小为 x 的俄罗斯娃娃里面可能会放任意多个大小小于 x 的俄罗斯娃娃(而市场上的套娃一般大娃里只能放一个小娃)。

        drd 告诉 atm ,这个俄罗斯娃娃是由 n 个小娃娃组成的,它们的大小各不相同。    我们把这些小娃娃的大小从小到大依次记为 1 到 n 。

        如果 atm 想观赏大小为 k 的小娃娃,他会先看这个小娃娃是否已经在桌子上了。    如果已经在桌子上,那么他就可以观赏了。否则他就打开桌子上某一个俄罗斯娃娃,将它套住的所有的小娃娃拿出来,摆在桌子上。
        一开始桌子上只有 drd 送的大小为 n 的娃娃。注意,他只会将其中所有小娃娃拿出来,如果小娃娃里面还套着另外的小娃娃,他是不会将这些更里层的这些小娃娃拿出来的。
        而且 atm 天生具有最优化的强迫症。他会最小化他所需要打开的娃娃的数目。

        atm 是一个怪人。有时候他只想知道观看大小为 x 的娃娃时需要打开多少个娃娃(但并不去打开);有时候听 drd 说某个娃娃特别漂亮,于是他会打开看。现在请你输出他每次需要打开多少个娃娃。
    输入
    第一行两个数 n m ,表示娃娃的数目以及 atm 想看的娃娃的数目。
    接下来 n - 1 行,每行两个数 u v,表示大小为 u 的娃娃里面套着一个大小为 v 的娃娃。保证 u > v 。
    接下来 m 行,每行形如:
      P x :表示 atm 一定要看到大小为 x 的娃娃;
      Q x :表示 atm 只想知道为了看大小为 x 的娃娃,他需要打开多少个娃娃,但实际上并不打开他们。
     
    输出
    输出 m 行。对应输入中P操作或Q操作需要打开(或假想打开)多少个俄罗斯娃娃。
    样例输入
    5 5
    5 3
    5 4
    3 2
    3 1
    Q 1
    Q 4
    P 2
    Q 1
    Q 4
    
    样例输出
    2
    1
    2
    0
    0
    #include<iostream>
    #include<algorithm>
    #include<queue>
    #include<vector>
    using namespace std;
    const int maxn = 1000010;
    struct Node{
        int depth;
        vector<int>next;
        int pre;
    }nodes[maxn];
    int n,m;
    void update(int index);
    int main(void)
    {
        cin >> n >> m;
        for(int i=1;i<=n;i++)
        {
            nodes[i].depth = 0;
            nodes[i].pre = i;
        }
        for(int i=0;i<n-1;i++)
        {
            int u,v;
            cin >> u >> v;
            nodes[v].pre = u;
            nodes[u].next.push_back(v);
        }
        
        for(int i=1;i<=n;i++)
        {
            int depth = 0,k=i;
            while(nodes[k].pre!=k)
            {
                depth++;
                k = nodes[k].pre;
            }
            nodes[i].depth = depth;
        }
        /* 
        cout << endl;
        for(int i=1;i<=n;i++)
        {
            cout << nodes[i].depth<<" ";
        }
        cout << endl;
        */ 
        for(int i=1;i<=m;i++)
        {
            string cm;
            int index;
            cin >> cm >> index;
            cout <<nodes[index].depth;
            if(i!=m) cout << endl;
            if(cm[0]=='P')
            {
                if(nodes[index].depth==0)
                {
                    
                }
                else
                {
                    //将本节点和所有父节点保存 
                    vector<int>father;
                    int k = i;
                    while(nodes[k].pre!=k)
                    {
                        father.push_back(k);
                        int temp = k;
                        k = nodes[k].pre;
                        nodes[temp].pre = temp;
                    }
                    father.push_back(k);
                    
                    //从最上次的节点开始,进行更新,每次更新需要把自己的后继节点全部释放 
                    int size = father.size();
                    for(k=0;k<size;k++)
                    {
                        update(father[size-1-k]);
                    }
                }
            }
            /* 
            cout << endl;
            for(int k=1;k<=n;k++)
            {
                cout << nodes[k].depth<<" ";
            }
            cout << endl;
            */ 
        }
        return 0;
    } 
    void update(int index)
    {
        queue<int>que;
        for(int i=0;i<nodes[index].next.size();i++)
        {
            que.push(nodes[index].next[i]);
        }
        nodes[index].next.clear();
        
        while(!que.empty())
        {
            int u = que.front(); que.pop();
            nodes[u].depth--;
            if(nodes[u].depth==0) nodes[u].pre = u;
            for(int i=0;i<nodes[u].next.size();i++)
            {
                que.push(nodes[u].next[i]);    
            } 
        }    
    }

    这是错误的,当然可能是正确的,但是时间复杂度太高了。

  • 相关阅读:
    c++ 两个set合并
    L2-2 小字辈 (25 分)
    L1-1 天梯赛座位分配
    c++ 用 0x3f3f3f3f 设定最大int值的优点
    Treap(树堆)(转)
    new一个二维数组(转)
    Laplacian matrix(转)
    寒假计划制定
    寒假集训日志(八,九,十)——浪浪浪
    寒假集训日志(七)——数据结构
  • 原文地址:https://www.cnblogs.com/zuimeiyujianni/p/10124719.html
Copyright © 2011-2022 走看看