HLG 1460 Highway Construction【树的直径】

题意: 已知一个树形的地图,要在其间建设一条公路,每个公路上的点只经过一次,问如何建工路使得所有点到公路的最长距离最短。

分析: 看成是找树上所有点中距离最远的路径,主要是两次广搜,第一次找到一个端点,第二次找到另一个,第二次找的过程中记录路径,

         便于最后一次遍历全图找到答案。

#include <stdio.h>
#include <string.h>
#define maxn 100005
#define clr(x)memset(x,0,sizeof(x))
struct node
{
    int to, next, w;
}q[1000000];
int tot;
int head[maxn];

void add(int s, int u, int wi)
{
    q[tot].to = u;
    q[tot].next = head[s];
    q[tot].w = wi;
    head[s] = tot++;
}

struct P
{
    int xu, di;
}que[maxn],xx,tt;

bool v[maxn];
int pre[maxn];
int main()
{
    int n, i, e, st;
    int front, rear, son;
    int a, b, wi;
    int tmp, res;
    while (scanf("%d",&n),n)
    {
        tot = 1;
        clr(head);
        for (i=0; i<n-1; i++)
        {
            scanf("%d %d %d",&a, &b, &wi);
            add(a, b, wi);
            add(b, a, wi);
        }

        tmp = 0;
        clr(v);
        front = rear = 0;
        tt.xu = 1;
        tt.di = 0;
        que[rear++] = tt;
        v[tt.xu] = true;

        while (front < rear)
        {
            xx = que[front++];
            for(i=head[xx.xu]; i; i=q[i].next)
            {
                tt.xu = q[i].to;
                if (!v[tt.xu])
                {
                    tt.di = xx.di + q[i].w;
                    v[tt.xu] = true;
                    que[rear++] = tt;
                    if(tt.di > tmp)
                    {
                        tmp = tt.di;
                        st = tt.xu;
                    }
                }
            }
        }

        front = rear = 0;
        tt.xu = st;
        tt.di = 0;
        que[rear++] = tt;
        clr(pre);
        pre[tt.xu] = -1;
        tmp = 0;

        while (front < rear)
        {
            xx = que[front++];
            for (i=head[xx.xu]; i; i=q[i].next)
            {
                tt.xu = q[i].to;
                if (!pre[tt.xu])
                {
                    tt.di = xx.di+q[i].w;
                    pre[tt.xu] = xx.xu;
                    que[rear++] = tt;
                    if (tt.di > tmp)
                    {
                        tmp = tt.di;
                        st = tt.xu;
                    }
                }
            }
        }

        clr(v);
        e = st;
        v[st] = true;
        while (pre[st] != -1)
        {
            v[pre[st]] = true;
            st = pre[st];
        }

        res = 0;
        front = rear = 0;
        while (pre[e] != -1)
        {
            e = pre[e];
            tt.xu = e;
            tt.di = 0;
            front = rear = 0;
            que[rear++] = tt;
            while (front < rear)
            {
                xx = que[front++];
                for (i=head[xx.xu]; i; i=q[i].next)
                {
                    tt.xu = q[i].to;
                    if (!v[tt.xu])
                    {
                        tt.di = q[i].w+xx.di;
                        v[tt.xu] = true;
                        que[rear++] = tt;
                        if (tt.di > res)
                            res = tt.di;
                    }
                }
            }
        }
        printf("%d\n",res);
    }
    return 0;
}

 

posted @ 2012-11-02 23:51  'wind  阅读(183)  评论(0编辑  收藏  举报