zoukankan      html  css  js  c++  java
  • Aizu 2677 Breadth-First Search by Foxpower LCA+bfs

    A - Breadth-First Search by Foxpower

    Problem Statement

    Fox Ciel went to JAG Kingdom by bicycle, but she forgot a place where she parked her bicycle. So she needs to search it from a bicycle-parking area before returning home.

    The parking area is formed as a unweighted rooted tree TT with nn vertices, numbered 11 through nn. Each vertex has a space for parking one or more bicycles. Ciel thought that she parked her bicycle near the vertex 11, so she decided to search it from there by the breadth-first search. That is, she searches it at the vertices in the increasing order of their distances from the vertex 11. If multiple vertices have the same distance, she gives priority to the vertices in the order of searching at their parents. If multiple vertices have the same parent, she searches at the vertex with minimum number at first.

    Unlike a computer, she can't go to a next vertex by random access. Thus, if she goes to the vertex jj after the vertex ii, she needs to walk the distance between the vertices ii and jj. BFS by fox power perhaps takes a long time, so she asks you to calculate the total moving distance in the worst case starting from the vertex 11.

    Input

    The input is formatted as follows.

    nn
    p2p2 p3p3 p4p4 ⋯ pnpn

    The first line contains an integer nn (1n1051≤n≤105), which is the number of vertices on the unweighted rooted tree TT. The second line contains n1n−1 integers pipi (1pi<i1≤pi<i), which are the parent of the vertex ii. The vertex 11 is a root node, so p1p1 does not exist.

    Output

    Print the total moving distance in the worst case in one line.

    Sample Input 1

    4
    1 1 2

    Output for the Sample Input 1

    6

    Sample Input 2

    4
    1 1 3

    Output for the Sample Input 2

    4

    Sample Input 3

    11
    1 1 3 3 2 4 1 3 2 9

    Output for the Sample Input 3

    25
    思路:求出出队序列,两两求树内最近距离;
    #include<bits/stdc++.h>
    using namespace std;
    #define ll long long
    #define mod 1000000007
    #define esp 0.00000000001
    const int N=2e5+10,M=1e6+10,inf=1e9;
    #define mem(s) memset(s,0,sizeof(s))
    int n,m,head[N],t,vis[N],deep[N],fa[N][20];
    int a[N];
    int flag[N];
    struct ss {
      int to,next;
    }e[N*2];
    void add(int u,int v) {
       e[t].next=head[u];e[t].to=v;head[u]=t++;
    }
    void init() {
      t=1;mem(head);mem(vis);mem(fa);mem(deep);mem(flag);
    }
    void dfs(int x) {
        vis[x]=1;
        for (int i=1; i<=18 ;i++) {
            if(deep[x]<(1<<i)) break;
            fa[x][i] = fa[fa[x][i-1]][i-1];
        }
        for (int i=head[x];i;i=e[i].next) {
            if(vis[e[i].to]) continue;
            deep[e[i].to]=deep[x]+1;
            fa[e[i].to][0]=x;
            dfs(e[i].to);
        }
    }
    int RMQ_LCA(int x,int y) {
        if(deep[x]<deep[y]) swap(x,y);
        int d=deep[x]-deep[y];
        for (int i=0; i<=18 ;i++)
            if((1<<i)&d) x=fa[x][i];
        for (int i=18; i>=0 ;i--) {
            if(fa[x][i]!=fa[y][i]) {
                x=fa[x][i];y=fa[y][i];
            }
        }
        if(x==y) return x;
        else return fa[x][0];
    }
    int Dis_LCA(int x,int y) {
        int LCA= RMQ_LCA(x,y);
        return (deep[x]+deep[y]-2*deep[LCA]);
    }
    struct is
    {
        int pos,step,pre;
    };
    int main()
    {
        int x,y,z,i,t;
        while(~scanf("%d",&x))
        {
            queue<is>q;
            init();
            for(i=2;i<=x;i++)
            scanf("%d",&a[i]);
            for(i=x;i>=2;i--)
            {
                add(a[i],i);
                add(i,a[i]);
            }
            dfs(1);
            int maxdeep=0;
            int pre=0;
            is st;
            st.pos=1;
            st.step=0;
            st.pre=0;
            q.push(st);
            flag[1]=1;
            ll ans=0;
            while(!q.empty())
            {
                is vv=q.front();
                q.pop();
                if(vv.pos!=1)
                {
                    ans+=Dis_LCA(vv.pos,pre);
                }
                pre=vv.pos;
                maxdeep=vv.step;
                int pos=vv.pos;
                for(i=head[vv.pos];i;i=e[i].next)
                {
                    if(flag[e[i].to])
                    continue;
                    is en;
                    en.pos=e[i].to;
                    en.step=vv.step+1;
                    en.pre=vv.pos;
                    flag[e[i].to]=1;
                    q.push(en);
                }
            }
            printf("%lld
    ",ans);
        }
        return 0;
    }
  • 相关阅读:
    4年Java程序员十面阿里终拿下offer,评级P6+年薪30-40w无股票
    真香警告!手绘172张图解HTTP协议+703页TCP/IP协议笔记
    Git官方和创始人都推荐的Git权威指南,广度深度和实战性史无前例
    阿里“教授”总结整理手写大型网站技术架构:核心原理与案例分析
    GitHub上120K Stars国内第一的Java多线程PDF到底有什么魅力?
    霸榜GitHub必读书籍:编写高质量代码改善Java程序员的151个建议
    GitHub上260K Stars的P8架构师纯手写的Java高并发编程详解
    LeetCode每日一题:802 找到最终安全状态
    LeetCode每日一题:662二叉树最大宽度
    Springboot之security框架 登录安全验证授权流程
  • 原文地址:https://www.cnblogs.com/jhz033/p/5671314.html
Copyright © 2011-2022 走看看