树的合并 connect
树的合并 connect
题目描述
话说moreD经过不懈努力,终于背完了循环整数,也终于完成了他的蛋糕大餐。
但是不幸的是,moreD得到了诅咒,受到诅咒的原因至今无人知晓。
moreD在发觉自己得到诅咒之后,决定去寻找闻名遐迩的术士CD帮忙。
话说CD最近在搞OI,遇到了一道有趣的题目:
给定两棵树,则总共有N*M种方案把这两棵树通过加一条边连成一棵树,那这N*M棵树的直径大小之和是多少呢?
CD为了考验moreD是否值得自己费心力为他除去诅咒,于是要他编程回答这个问题,但是这moreD早就被诅咒搞晕了头脑,就只好请你帮助他了。
输入
第一行两个正整数N,M,分别表示两棵树的大小。
接下来N-1行,每行两个正整数ai,bi,表示第一棵树上的边。
接下来M-1行,每行两个正整数ci,di,表示第二棵树上的边。
输出
一行一个整数,表示答案。
样例输入
4 3
1 2
2 3
2 4
1 3
2 3
样例输出
53
提示
【数据范围】
对于20%的数据满足N<=300,M<=300
对于50%的数据满足N,M<=3000
对于100%的数据满足N<=10^5,M<=10^5,1<=ai,bi<=N,1<=ci,di<=M
【提示】
树的直径指的是树上的最长简单路径。
来源
挺好想的题
令a[i]表示i开头第一棵树上最长链
b[i]表示i开头第二棵树上最长链
Max为两棵树直径的max
对于a[i]和b[j]
贡献为max(Max,a[i]+b[j]+1)
拿个指针扫扫就行了
#include<cstdio>
#include<iostream>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#include<cmath>
#define maxn 100005
using namespace std;
int n,m,tot,head[maxn],f[maxn],g[maxn],dp[maxn],t1,t2;
long long a[maxn],b[maxn],sum[maxn],ans,ma;
struct node{
int v,nex;
}e[maxn*2];
void lj(int t1,int t2){
tot++;e[tot].v=t2;e[tot].nex=head[t1];head[t1]=tot;
}
void dfs1(int k,int fa){
int Max=-1e9,max2=-1e9;
for(int i=head[k];i;i=e[i].nex){
if(e[i].v!=fa){
dfs1(e[i].v,k);
if(f[e[i].v]>Max){
max2=max(max2,Max);
Max=f[e[i].v];
}
else max2=max(max2,f[e[i].v]);
}
}
if(Max==-1e9)f[k]=0,g[k]=-1e9;
else {f[k]=Max+1;g[k]=max2+1;}
//cout<<k<<' '<<f[k]<<' '<<g[k]<<endl;
}
void dfs2(int k,int fa){
for(int i=head[k];i;i=e[i].nex){
if(e[i].v!=fa){
dp[e[i].v]=max(dp[e[i].v],dp[k]+1);
if(f[e[i].v]==f[k]-1){
dp[e[i].v]=max(dp[e[i].v],g[k]+1);
}
else dp[e[i].v]=max(dp[e[i].v],f[k]+1);
dfs2(e[i].v,k);
}
}
}
void Q(){
for(int i=1;i<=n;i++)head[i]=f[i]=g[i]=dp[i]=0;
tot=0;
}
int main()
{
cin>>n>>m;
for(int i=1;i<n;i++){
scanf("%d%d",&t1,&t2);
lj(t1,t2);lj(t2,t1);
}
dfs1(1,0);dfs2(1,0);
for(int i=1;i<=n;i++)a[i]=max(f[i],dp[i]);
Q();
for(int i=1;i<m;i++){
scanf("%d%d",&t1,&t2);
lj(t1,t2);lj(t2,t1);
}
dfs1(1,0);dfs2(1,0);
for(int i=1;i<=m;i++){
b[i]=max(f[i],dp[i]);
}
sort(a+1,a+n+1);sort(b+1,b+m+1);
for(int i=1;i<=n;i++)sum[i]=sum[i-1]+a[i];
ma=max(a[n],b[m]);
int l=1;
for(int i=m;i>=1;i--){
while(b[i]+a[l]+1<ma&&l<=n)l++;
long long num=n-l+1;
long long tmp=b[i]*num;tmp+=sum[n]-sum[l-1];tmp+=num;
tmp+=ma*(n-num);
ans+=tmp;
}
cout<<ans<<endl;
return 0;
}
树的合并 connect的更多相关文章
- 【主席树 启发式合并】bzoj3123: [Sdoi2013]森林
小细节磕磕碰碰浪费了半个多小时的时间 Description Input 第一行包含一个正整数testcase,表示当前测试数据的测试点编号.保证1≤testcase≤20. 第二行包含三个整数N,M ...
- [CSP-S模拟测试]:模板(ac)(线段树启发式合并)
题目描述 辣鸡$ljh\ NOI$之后就退役了,然后就滚去学文化课了.他每天都被$katarina$大神虐,仗着自己学过一些姿势就给$katarina$大神出了一道题.有一棵$n$个节点的以$1$号节 ...
- POJ 3667 Hotel(线段树 区间合并)
Hotel 转载自:http://www.cnblogs.com/scau20110726/archive/2013/05/07/3065418.html [题目链接]Hotel [题目类型]线段树 ...
- HDU 3911 线段树区间合并、异或取反操作
题目:http://acm.hdu.edu.cn/showproblem.php?pid=3911 线段树区间合并的题目,解释一下代码中声明数组的作用: m1是区间内连续1的最长长度,m0是区间内连续 ...
- HDU 3911 Black And White(线段树区间合并+lazy操作)
开始以为是水题,结果...... 给你一些只有两种颜色的石头,0为白色,1为黑色. 然后两个操作: 1 l r 将[ l , r ]内的颜色取反 0 l r 计算[ l , r ]内最长连续黑色石头的 ...
- SPOJ COT3 Combat on a tree(Trie树、线段树的合并)
题目链接:http://www.spoj.com/problems/COT3/ Alice and Bob are playing a game on a tree of n nodes.Each n ...
- HYSBZ 1858 线段树 区间合并
//Accepted 14560 KB 1532 ms //线段树 区间合并 /* 0 a b 把[a, b]区间内的所有数全变成0 1 a b 把[a, b]区间内的所有数全变成1 2 a b 把[ ...
- poj3667 线段树 区间合并
//Accepted 3728 KB 1079 ms //线段树 区间合并 #include <cstdio> #include <cstring> #include < ...
- hdu3911 线段树 区间合并
//Accepted 3911 750MS 9872K //线段树 区间合并 #include <cstdio> #include <cstring> #include < ...
随机推荐
- js 常用工具类
/** * 存储sessionStorage */const setStore = (name, content) => { window.sessionStorage.setItem(name ...
- PageHelper 记录总条数不正确问题处理
//PageHelper.startPage会返回一个page对象,这个对象在查询结果出来后会把页数,记录总数给page对象,用page.getPages()和getTotal()获取页数和记录总数. ...
- JSPatch - iOS 动态补丁
JSPatch库,支持在线更新iOS应用,目前BDN项目中有用到,主要用来修复线上Crash和Bug 相关博文推荐: JSPatch – 动态更新iOS APP(这是JSPatch作者的博文) JSP ...
- SQL Server数据库日志清除
第一步 将数据库转换成 simple 模式 USE master GO ALTER DATABASE 所要删除日志的数据库名 SET RECOVERY SIMPLE WITH NO_WAIT GO 第 ...
- ES6学习(二):函数的扩展
chapter07 函数的扩展 7.1 函数默认值 7.1.1 参数默认值简介 传统做法的弊端(||):如果传入的参数相等于(==)false的话,仍会被设为默认值,需要多加入一个if判断,比较麻烦. ...
- 解决: Intelij IDEA 创建WEB项目时没有Servlet的jar包
今天创建SpringMVC项目时 用到HttpServletRequest时, 发现项目中根本没有Servlet这个包, 在网上搜了一下,这个问题是因为web项目没有添加服务器导致的. 配置tomec ...
- 虚拟机Linux_Mint中安装vmtools增强工具
一开始用VmwarePro安装Linux系统时,系统的整体界面会缩在屏幕中间的一小块区域内.如图: 看的会非常吃力.为了更好的解决这个问题,就需要安装Vmtools增强工具.安装步骤如下: 1. ...
- SAP后台JOB的Submit & EVENT JOB
SM35执行一个后台作业后,想及时停止, 运行SM37后,点击ctr + F1停止活动的作业,系统根本就没反应. 解决方法: 第一步:SM50, 找到,Ty.列为BGD的(Background),然后 ...
- .net core IdentityServer4 使用query参数
基本用法请参考官方文档:https://identityserver4.readthedocs.io/en/latest/index.html 这里不对具体用法进行说明,一般情况下,Startup添加 ...
- 洛谷 P2279 [HNOI2003]消防局的设立
题目描述 2020年,人类在火星上建立了一个庞大的基地群,总共有n个基地.起初为了节约材料,人类只修建了n-1条道路来连接这些基地,并且每两个基地都能够通过道路到达,所以所有的基地形成了一个巨大的树状 ...