• Codeforces Round #328 (Div. 2) D. Super M 虚树直径


    D. Super M

    Time Limit: 20 Sec

    Memory Limit: 256 MB

    题目连接

    http://codeforces.com/contest/592/problem/D

    Description

    Ari the monster is not an ordinary monster. She is the hidden identity of Super M, the Byteforces’ superhero. Byteforces is a country that consists of n cities, connected by n - 1 bidirectional roads. Every road connects exactly two distinct cities, and the whole road system is designed in a way that one is able to go from any city to any other city using only the given roads. There are m cities being attacked by humans. So Ari... we meant Super M have to immediately go to each of the cities being attacked to scare those bad humans. Super M can pass from one city to another only using the given roads. Moreover, passing through one road takes her exactly one kron - the time unit used in Byteforces.

    However, Super M is not on Byteforces now - she is attending a training camp located in a nearby country Codeforces. Fortunately, there is a special device in Codeforces that allows her to instantly teleport from Codeforces to any city of Byteforces. The way back is too long, so for the purpose of this problem teleportation is used exactly once.

    You are to help Super M, by calculating the city in which she should teleport at the beginning in order to end her job in the minimum time (measured in krons). Also, provide her with this time so she can plan her way back to Codeforces.

    Input

    The first line of the input contains two integers n and m (1 ≤ m ≤ n ≤ 123456) - the number of cities in Byteforces, and the number of cities being attacked respectively.

    Then follow n - 1 lines, describing the road system. Each line contains two city numbers ui and vi (1 ≤ ui, vi ≤ n) - the ends of the road i.

    The last line contains m distinct integers - numbers of cities being attacked. These numbers are given in no particular order.

     

    Output

    First print the number of the city Super M should teleport to. If there are many possible optimal answers, print the one with the lowest city number.

    Then print the minimum possible time needed to scare all humans in cities being attacked, measured in Krons.

    Note that the correct answer is always unique.

    Sample Input

    7 2
    1 2
    1 3
    1 4
    3 5
    3 6
    3 7
    2 7

    Sample Output

    2
    3

    HINT

    题意

    给你一棵树,树上有一些重要的点,超人必须要去。

    然后让你选择一个点作为起点,使得从这个点开始遍历其他的重要的点要走的距离最小

    如果有多个解,就输出最小的那个

    题解:

    相当于建一颗包含所有重要的点,但是大小最小的虚树,然后再那个虚树里面找到字典序最小的直径

    然后答案就是2*边长-直径长度就好了

    代码

    #include<iostream>
    #include<stdio.h>
    #include<vector>
    #include<cstring>
    using namespace std;
    #define maxn 123459
    vector<int>Q[maxn];
    int vis[maxn];
    int vis2[maxn];
    int ans1,ans2,len;
    void dfs(int x,int dis,int pre)
    {
        if(dis>len&&vis[x])
        {
            len = dis;
            ans2 = x;
        }
        if(dis==len&&vis[x]&&x<ans2)
            ans2 = x;
        for(int i=0;i<Q[x].size();i++)
        {
            if(Q[x][i]==pre)
                continue;
            dfs(Q[x][i],dis+1,x);
        }
    }
    int ppp = 0;
    int dfs2(int x,int pre)
    {
        if(vis[x])vis2[x]++;
        for(int i=0;i<Q[x].size();i++)
        {
            if(Q[x][i]==pre)
                continue;
            vis2[x]+=dfs2(Q[x][i],x);
        }
        return vis2[x];
    }
    void dfs3(int x,int pre)
    {
        if(vis2[x])
            ppp++;
        for(int i=0;i<Q[x].size();i++)
        {
            if(Q[x][i]==pre)
                continue;
            dfs3(Q[x][i],x);
        }
    }
    int main()
    {
        int n,m;scanf("%d%d",&n,&m);
        for(int i=1;i<n;i++)
        {
            int x,y;scanf("%d%d",&x,&y);
            Q[x].push_back(y);
            Q[y].push_back(x);
        }
        ans1 = 99999999;
        for(int i=1;i<=m;i++)
        {
            int x;scanf("%d",&x);
            vis[x]=1;
            ans1 = min(x,ans1);
        }
        if(m==1)
        {
            printf("%d
    0
    ",ans1);
            return 0;
        }
        len = -1;
        dfs(ans1,0,-1);
        ans1 = ans2;
        len = -1;
        dfs(ans1,0,-1);
        dfs2(ans2,-1);
        dfs3(ans2,-1);
        printf("%d
    ",min(ans1,ans2));
        if(ppp!=1)ppp--;
        printf("%d
    ",ppp*2 - len);
    }
  • 相关阅读:
    HttpApplication处理对象与HttpModule处理模块
    HttpHandler与HttpModule的用处与区别
    ASP.NET管线与应用程序生命周期
    IIS架构与HTTP请求处理流程
    构造函数的选择与服务生命周期管理
    堆排序
    WebApi异常
    Java NIO内存映射---上G大文件处理(转)
    Spring+Mybatis+SpringMVC后台与前台分页展示实例(附工程)(转)
    redis入门(转)
  • 原文地址:https://www.cnblogs.com/qscqesze/p/4928045.html
Copyright © 2020-2023  润新知