题目大意:

每一条边都有两个权值,val和路径长度d,要保证在val<=m 的条件下,求最长的d.

解题报告:

一开始想错了,后来发现还不如直接暴力点分,思想很套路..

平时我们统计时,都会用合法减不合法,但这题不是方案统计,需要枚举每一棵子树,这里其实直接暴力枚就行,但是用到了val和d的单调性,首先明确:如果对于两条路径i,j:\(vali>valj,di<dj\) 这样显然不会最优,所以我们就去掉这些路径,剩下的就满足单调性了,d随val增加而增加,这样就可以二分了.

所以我们把子树分为两个部分,一部分是已经处理好的,另一部分是未知的集合e,我们枚举处理好的集合c,然后将e按val从小到大排序后,二分最大满足\(val_c+val_e<=m\) 的e,此时的e一定是d最大的,更新答案后,我们再把e加入到c集合中,此时c集合依旧满足单调性.

复杂度\(O(TNlog2N)\)

#include <algorithm>
#include <iostream>
#include <cstdlib>
#include <cstring>
#include <cstdio>
#include <cmath>
#define RG register
#define il inline
#define iter iterator
#define Max(a,b) ((a)>(b)?(a):(b))
#define Min(a,b) ((a)<(b)?(a):(b))
#define ls (node<<1)
#define rs (node<<1|1)
using namespace std;
const int N=30005,inf=100000005;
int gi(){
int str=0;char ch=getchar();
while(ch>'9' || ch<'0')ch=getchar();
while(ch>='0' && ch<='9')
str=(str<<1)+(str<<3)+ch-48,ch=getchar();
return str;
}
int m,head[N],num=0,to[N<<1],nxt[N<<1],dis[N<<1],c[N<<1],n,ans=0;
int f[N]={inf},root=0,son[N],sum,sz=0,CNT=0;bool vis[N];
void link(int x,int y,int z,int k){
nxt[++num]=head[x];to[num]=y;dis[num]=z;c[num]=k;
head[x]=num;
}
il void getroot(int x,int last){
int u;son[x]=1;f[x]=0;
for(int i=head[x];i;i=nxt[i]){
u=to[i];if(u==last || vis[u])continue;
getroot(u,x);
son[x]+=son[u];
f[x]=Max(f[x],son[u]);
}
f[x]=Max(f[x],sum-son[x]);
if(f[x]<f[root])root=x;
}
struct node{
int d,c;
bool operator<(const node &pp)const{
return d<pp.d;
}
}v[N];
il void getdis(int x,int last,int dist,int cost){
int u;
v[++sz].d=dist;v[sz].c=cost;
for(int i=head[x];i;i=nxt[i]){
u=to[i];if(u==last || vis[u])continue;
getdis(u,x,dist+dis[i],cost+c[i]);
}
}
int q[N][2],tot=0;
void Unique(){
int p=0,mx=0;
sort(v+1,v+sz+1);
for(int i=1;i<=sz;i++){
if(v[i].c<=mx)continue;
else {
v[++p]=v[i];
mx=v[i].c;
}
}
sz=p;
}
int midit(int x){
int l=1,r=sz,mid,ret=-1;
while(l<=r){
mid=(l+r)>>1;
if(x+v[mid].d<=m)ret=mid,l=mid+1;
else r=mid-1;
}
return ret;
}
void cal(){
Unique();
int tmp;
for(int i=1;i<=tot;i++){
tmp=midit(q[i][0]);if(tmp==-1)continue;
if(v[tmp].c+q[i][1]>ans)ans=v[tmp].c+q[i][1];
}
for(int i=1;i<=sz;i++){
q[++tot][0]=v[i].d;q[tot][1]=v[i].c;
}
sz=0;
}
il void solve(int x){
int u;tot=0;
for(int i=head[x];i;i=nxt[i]){
u=to[i];if(vis[u])continue;
getdis(u,x,dis[i],c[i]);
cal();
}
}
il void dfs(int x){
int u;vis[x]=true;
solve(x);
for(int i=head[x];i;i=nxt[i]){
u=to[i];if(vis[u])continue;
sum=son[u];root=0;getroot(u,x);
dfs(root);
}
}
void Clear(){
num=0;ans=0;memset(head,0,sizeof(head));
memset(vis,0,sizeof(vis));
}
void work()
{
Clear();
int x,y,z,r;
n=gi();m=gi();
for(int i=1;i<n;i++){
x=gi();y=gi();z=gi();r=gi();
link(x,y,z,r);link(y,x,z,r);
}
root=0;sum=n;getroot(1,1);
dfs(root);
printf("Case %d: %d\n",CNT,ans);
} int main()
{
int T=gi();
while(T--)CNT++,work();
return 0;
}

UVA 12161 Ironman Race in Treeland的更多相关文章

  1. UVA 12161 Ironman Race in Treeland (树分治)

    题意:求树上的一条费用不超过m的路径,使得总长度尽量大. 人参第一发树分治,紫书上思路讲得比较清晰,这里不再赘述. 实现的时候,用一个类似时间戟的东西,记录结点首次访问的时间,并保存结点序列. 合并的 ...

  2. UVA 10627 - Infinite Race(数论)

    UVA 10627 - Infinite Race option=com_onlinejudge&Itemid=8&page=show_problem&category=516 ...

  3. bzoj AC倒序

    Search GO 说明:输入题号直接进入相应题目,如需搜索含数字的题目,请在关键词前加单引号 Problem ID Title Source AC Submit Y 1000 A+B Problem ...

  4. UVA 11762 - Race to 1(概率)

    UVA 11762 - Race to 1 题意:给定一个n,每次随即选择一个n以内的质数,假设不是质因子,就保持不变,假设是的话.就把n除掉该因子,问n变成1的次数的期望值 思路:tot为总的质数. ...

  5. UVa 11762 - Race to 1

    http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&p ...

  6. 【UVA】【11762】Race to 1(得到1)

    数学期望/马尔可夫过程 DP/记忆化搜索 刘汝佳老师白书上的例题…… //UVA 11762 #include<vector> #include<cstdio> #includ ...

  7. [uva 11762]Race to 1[概率DP]

    引用自:http://hi.baidu.com/aekdycoin/item/be20a91bb6cc3213e3f986d3,有改动 题意: 已知D, 每次从[1,D] 内的所有素数中选择一个Ni, ...

  8. UVa 12034 - Race(递推 + 杨辉三角)

    链接: https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem& ...

  9. Race UVA - 12034(dp+打表)

    Disky and Sooma, two of the biggest mega minds of Bangladesh went to a far country. They ate, coded ...

随机推荐

  1. HP DL380服务器RAID信息丢失数据恢复方法和数据恢复过程分享

    [数据恢复故障描述]    客户服务器属于HP品牌DL380系列,存储是由6块73GB SAS硬盘组成的RAID5,操作系统是WINDOWS 2003 SERVER,主要作为企业部门内部的文件服务器来 ...

  2. MySQL搭建主从数据库 实现读写分离

    首先声明,实际生产中,网站为了提高用户体验,性能等,将数据库实现读写分离是有必要的,我们让主数据库去写入数据,然后当用户查询的时候,然后在从数据库读取数据,故能减轻数据库的压力,实现良好的用户体验! ...

  3. Java 持久化之 --io流与序列化操作

    1)File类操作文件的属性 1.File类的常用方法 1. 文件的绝对完整路径:getAbsolutePath() 文件名:getName() 文件相对路径:getPath() 文件的上一级目录:g ...

  4. HttpClient 上传多个文件

    using (System.Net.Http.HttpClient client = new System.Net.Http.HttpClient()) { client.BaseAddress = ...

  5. H5 FormData对象的作用及用法

    JS: function uploadFileAndParam() { var url = "http://localhost:42561/api/upload/UploadPost&quo ...

  6. WebApi 接口返回值类型详解 ( 转 )

    使用过Webapi的园友应该都知道,Webapi的接口返回值主要有四种类型 void无返回值 IHttpActionResult HttpResponseMessage 自定义类型 此篇就围绕这四块分 ...

  7. iOS HTML图片本地预览

    引言 相信用过苹果手机的童鞋,会发现很多新闻类的应用,都可以实现HTML图片本地预览,那么这是如何实现的呢?本文将深入阐述其中的原理. 关于此功能,我还实现了一个DEMO,大家可以点击此访问更详细内容 ...

  8. DOM节点删除之empty和remove区别

    要移除页面上节点是开发者常见的操作,jQuery提供了几种不同的方法用来处理这个问题,这里我们开仔细了解下empty和remove方法 empty 顾名思义,清空方法,但是与删除又有点不一样,因为它只 ...

  9. C#使用Socket实现一个socket服务器与多个socket客户端通信

    在分布式调度系统中,如果要实现调度服务器与多台计算节点服务器之间通信,采用socket来实现是一种实现方式,当然我们也可以通过数据存储任务,子节点来完成任务,但是往往使用数据作为任务存储都需要定制开发 ...

  10. redis从入门到

    下载 首先我们要到GitHub(https://github.com/MicrosoftArchive/redis/releases)上下载Source code (tar.gz) 上传到Linux上 ...