• poj1741-Tree


    Description

    Give a tree with n vertices,each edge has a length(positive integer less than 1001). 
    Define dist(u,v)=The min distance between node u and v. 
    Give an integer k,for every pair (u,v) of vertices is called valid if and only if dist(u,v) not exceed k. 
    Write a program that will count how many pairs which are valid for a given tree. 

    Input

    The input contains several test cases. The first line of each test case contains two integers n, k. (n<=10000) The following n-1 lines each contains three integers u,v,l, which means there is an edge between node u and v of length l. 
    The last test case is followed by two zeros. 

    Output

    For each test case output the answer on a single line.

    Sample Input

    5 4
    1 2 3
    1 3 1
    1 4 2
    3 5 1
    0 0
    

    Sample Output

    8
    题意是给你一棵树,求长度不超过k的路径有多少条
    
    点分治
    如果指定节点p作为树的根,那么树上的路径就可以分为两类
    1.经过节点p
    2.不经过节点p
    根据分治的思想,对于第二类路径,显然可以把p的每棵子树作为子问题,递归处理
    而对于第一类路径
    对于这题,可以对这个点延伸出的几棵子树各做一次dfs记录子树中出现的距离值
    对于一棵树的距离值数组,把它排序求一次ans1,再对每棵子树分别求一个自己对自己的ans2,ans1−∑ans2即为最后的ans
    #include<iostream>
    #include<cstdio>
    #include<cstdlib>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    //#include<bits/stdc++.h>
    #define inf 0x3f3f3f3f
    using namespace std;
    const int N=1e5+10;
    struct orz{
        int v,nex,s;}e[N*2];
    int last[N],son[N],deep[N],f[N],d[N];
    int n,k,cnt,root,sum,ans;
    bool vis[N];
    void add(int x,int y,int z)
    {
        cnt++;
        e[cnt].v=y;
        e[cnt].nex=last[x];
        last[x]=cnt;
        e[cnt].s=z;
    }
    void getroot(int x,int fa) //找重心
    {
        son[x]=1; f[x]=0;
        for (int i=last[x];i;i=e[i].nex)
        {
            if (e[i].v==fa || vis[e[i].v]) continue;
            getroot(e[i].v,x);
            son[x]+=son[e[i].v];
            f[x]=max(f[x],son[e[i].v]);
        }
        f[x]=max(f[x],sum-son[x]);
        if (f[x]<f[root]) root=x;
    }
    void getdeep(int x,int fa) 
    {
        deep[++deep[0]]=d[x];
        for (int i=last[x];i;i=e[i].nex)
        {
            if (e[i].v==fa || vis[e[i].v]) continue;
            d[e[i].v]=d[x]+e[i].s;
            getdeep(e[i].v,x);
        }
    }
    int cal(int x,int now)
    {
        d[x]=now; deep[0]=0;
        getdeep(x,0);
        sort(deep+1,deep+deep[0]+1);
        int t=0,l,r;
        for (l=1,r=deep[0];l<r;)
        {
            if (deep[l]+deep[r]<=k)
            {
                t+=r-l; l++;
            }
            else r--;
        }
        return t;
    }
    void work(int x)
    {
        ans+=cal(x,0);
        vis[x]=1;
        for (int i=last[x];i;i=e[i].nex)
        {
            if (vis[e[i].v]) continue;
            ans-=cal(e[i].v,e[i].s);
            sum=son[e[i].v];
            root=0;
            getroot(e[i].v,root);
            work(root);
        }
    }
    int main()
    {
        while (scanf("%d%d",&n,&k)&&(n+k))
        {
            cnt=0; ans=0;
            memset(last,0,sizeof(last));
            memset(vis,0,sizeof(vis));
            int x,y,z;
            for (int i=1;i<n;i++)
            {
                scanf("%d%d%d",&x,&y,&z);
                add(x,y,z); add(y,x,z);
            }
            sum=n; f[0]=inf;
            getroot(1,0);
            work(root);
            printf("%d
    ",ans);
        }
        return 0;
    }
    View Code
  • 相关阅读:
    fastjson(转)
    FastJson
    FastJson处理Map List 对象
    spring-data-redis RedisTemplate操作
    Spring-data-redis:特性与实例(转载)
    Spring Boot 支持多种外部配置方式
    springBoot----@ConditionalOnxxx相关注解总结
    Centos7 install Openstack
    Centos7 install Openstack
    Centos7 Openstack
  • 原文地址:https://www.cnblogs.com/tetew/p/9839891.html
Copyright © 2020-2023  润新知