题意:找树上有多少对距离小于K的对数
解析:树分治模板题,见注释

代码

#include<cstdio>
#include<cstring>
#include<string>
#include<algorithm>
#include<vector>
using namespace std;
typedef __int64 LL;
const int INF=1e9+;
const int maxn=;
int N,K,ans;
struct edge{ int v,w,next; }E[*maxn]; //边
int head[maxn],eid;
void init()
{
ans=eid=;
for(int i=;i<=N;i++) head[i]=-;
}
void AddEdge(int u,int v,int w)
{
E[++eid].v=v; E[eid].w=w;
E[eid].next=head[u]; head[u]=eid;
}
struct TBS
{
int root,did,deep[maxn],dist[maxn]; //root选取的根
int tot,s[maxn],cen[maxn]; //s树的大小,cen左右两边的节点最大值
bool used[maxn]; //是否已被访问
void init(int n) //初始化
{
tot=n;
cen[]=INF;
memset(used,false,sizeof(used));
}
void GetRoot(int u,int fa)//找到重心
{
s[u]=; //树的大小
cen[u]=;
for(int i=head[u];i!=-;i=E[i].next)
{
int v=E[i].v;
if(v==fa||used[v]) continue;
GetRoot(v,u);
s[u]+=s[v];
cen[u]=max(cen[u],s[v]);
}
cen[u]=max(cen[u],tot-s[u]);
if(cen[u]<cen[root]) root=u; //更新重心
}
void GetDeep(int u,int fa)
{
deep[++did]=dist[u]; //保存下来
for(int i=head[u];i!=-;i=E[i].next)
{
int v=E[i].v,w=E[i].w;
if(v==fa||used[v]) continue;
dist[v]=dist[u]+w; //距离所选重心的距离
GetDeep(v,u);
}
}
int Cal(int u,int w)
{
dist[u]=w; did=;
GetDeep(u,);
sort(deep+,deep+did+);
int ret=;
for(int l=,r=did;l<r;)
{
if(deep[l]+deep[r]<=K){ ret+=r-l; l++; } //计算小于K的点对
else r--;
}
return ret;
}
void Work(int u)
{
used[u]=true;
ans+=Cal(u,);
for(int i=head[u];i!=-;i=E[i].next)
{
int v=E[i].v,w=E[i].w;
if(used[v]) continue;
ans-=Cal(v,w); //去重
tot=s[v];
root=;
GetRoot(v,u); //找下一个重心
Work(root);
}
}
}tbs;
int main()
{
while(scanf("%d%d",&N,&K)!=EOF)
{
if(!N&&!K) break;
init();
int u,v,w;
for(int i=;i<N;i++)
{
scanf("%d%d%d",&u,&v,&w);
AddEdge(u,v,w);
AddEdge(v,u,w);
}
tbs.init(N);
tbs.GetRoot(,);
tbs.Work(tbs.root);
printf("%d\n",ans);
}
return ;
}

Poj1741-Tree(树分治)的更多相关文章

  1. POJ1741 Tree 树分治模板

    http://poj.org/problem?id=1741   题意:一棵n个点的树,每条边有距离v,求该树中距离小于等于k的点的对数.   dis[y]表示点y到根x的距离,v代表根到子树根的距离 ...

  2. 【BZOJ-1468】Tree 树分治

    1468: Tree Time Limit: 10 Sec  Memory Limit: 64 MBSubmit: 1025  Solved: 534[Submit][Status][Discuss] ...

  3. HDU 4812 D Tree 树分治+逆元处理

    D Tree Problem Description   There is a skyscraping tree standing on the playground of Nanjing Unive ...

  4. POJ 1741 Tree 树分治

    Tree     Description Give a tree with n vertices,each edge has a length(positive integer less than 1 ...

  5. POJ 1741.Tree 树分治 树形dp 树上点对

    Tree Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 24258   Accepted: 8062 Description ...

  6. poj 1744 tree 树分治

    Tree Time Limit: 1000MS   Memory Limit: 30000K       Description Give a tree with n vertices,each ed ...

  7. HDU4871 Shortest-path tree(树分治)

    好久没做过树分治的题了,对上一次做是在南京赛里跪了一道很裸的树分治题后学的一道,多校的时候没有看这道题,哪怕看了感觉也看不出来是树分治,看出题人给了解题报告里写了树分治就做一下好了. 题意其实就是给你 ...

  8. HDU4670 Cube number on a tree 树分治

    人生的第一道树分治,要是早点学我南京赛就不用那么挫了,树分治的思路其实很简单,就是对子树找到一个重心(Centroid),实现重心分解,然后递归的解决分开后的树的子问题,关键是合并,当要合并跨过重心的 ...

  9. [POJ1741]Tree(点分治)

    树分治之点分治入门 所谓点分治,就是对于树针对点的分治处理 首先找出重心以保证时间复杂度 然后递归处理所有子树 对于这道题,对于点对(u,v)满足dis(u,v)<=k,分2种情况 路径过当前根 ...

  10. POJ1741 经典树分治

    题意:有一棵树,每条边有一个距离,求dis(u,v)<=k的点的对数 题解:树分治,对于一颗树上的两点,要么在同一颗子树上,要么在不同子树上,要么一个点是根,另一个在某一子树上,对于第一种情况我 ...

随机推荐

  1. sqlite3 C接口

  2. springmvc+mongodb+maven 项目搭建配置

    操作步骤我就不再细化了 项目能运行,测试过了,先上配置,另一篇文章上代码,点击下载源码 项目结构 pom.xml <project xmlns="http://maven.apache ...

  3. BNU10806:请在此处签到

    每年圣诞,ZUN都会邀请很多人到幻想乡举行联欢,今年也不例外.在联欢前,所有人需要在自己的昵称旁签到(签全名),以示出席.然后ZUN 会把大家的签到表保存下来作为纪念,以激励来年努力工作.   昵称: ...

  4. ibatis之##与$$的 使用

    /** 主要讲一下ibatis中$$的使用: 是为了传递参数; 参数一定在Action层用''包裹起来: */ List <SysRole> userList= systemService ...

  5. 远程连接到Fedora

    首先执行以下3点(主要是前两点) 第一: 开启ssh #service sshd restart 第二:关闭防火墙 #service iptables stop 第三:selinux(重启电脑后失效) ...

  6. 安装mysql时提示The host 'xxx' could not be looked up with resolveip的解决办法

    1.首先用cat查看/etc/hosts文件,会显示以下内容: 127.0.0.1 localhost localhost.localdomain localhost4 localhost4.loca ...

  7. 数据库分库分表(sharding)系列(五) 一种支持自由规划无须数据迁移和修改路由代码的Sharding扩容方案

    作为一种数据存储层面上的水平伸缩解决方案,数据库Sharding技术由来已久,很多海量数据系统在其发展演进的历程中都曾经历过分库分表的Sharding改造阶段.简单地说,Sharding就是将原来单一 ...

  8. 电脑文本text和部分文字出现其他语言乱码

     1.文本的编码存在问题 解决办法: 将text文件打开>>文件(左上角)>>另存为>>选择其他格式的编码试试(在保存键左侧)>>保存再打开 2.系统区 ...

  9. Linux上安装JDK

    1.下载rpm文件并安装 rpm -ivh jdk-7u51-linux-x64.rpm 2.修改/etc/profile文件,增加以下配置 export JAVA_HOME=/usr/java/jd ...

  10. 【干货】.NET开发通用组件发布(三) 简易数据采集组件

    组件介绍和合作开发 http://www.cnblogs.com/MrHuo/p/MrHuoControls.html 简易数据采集组件 怎么说他是一个简易的数据采集组件呢?因为由于时间仓促,缺少从某 ...