洛谷 P4408 逃学的小孩 解题报告
P4408 [NOI2003]逃学的小孩
题目描述
Chris家的电话铃响起了,里面传出了Chris的老师焦急的声音:“喂,是Chris的家长吗?你们的孩子又没来上课,不想参加考试了吗?”一听说要考试,Chris的父母就心急如焚,他们决定在尽量短的时间内找到Chris。他们告诉Chris的老师:“根据以往的经验,Chris现在必然躲在朋友Shermie或Yashiro家里偷玩《拳皇》游戏。现在,我们就从家出发去找Chris,一但找到,我们立刻给您打电话。”说完砰的一声把电话挂了。
Chris居住的城市由N个居住点和若干条连接居住点的双向街道组成,经过街道x需花费Tx分钟。可以保证,任两个居住点间有且仅有一条通路。Chris家在点C,Shermie和Yashiro分别住在点A和点B。Chris的老师和Chris的父母都有城市地图,但Chris的父母知道点A、B、C的具体位置而Chris的老师不知。
为了尽快找到Chris,Chris的父母会遵守以下两条规则:
如果A距离C比B距离C近,那么Chris的父母先去Shermie家寻找Chris,如果找不到,Chris的父母再去Yashiro家;反之亦然。
Chris的父母总沿着两点间唯一的通路行走。
显然,Chris的老师知道Chris的父母在寻找Chris的过程中会遵守以上两条规则,但由于他并不知道A,B,C的具体位置,所以现在他希望你告诉他,最坏情况下Chris的父母要耗费多长时间才能找到Chris?
输入输出格式
输入格式:
输入文件第一行是两个整数\(N(3 ≤ N ≤ 200000)\)和\(M\),分别表示居住点总数和街道总数。
以下\(M\)行,每行给出一条街道的信息。第\(i+1\)行包含整数\(U_i\)、\(V_i\)、\(T_i\) \((1≤U_i, V_i ≤ N,1 ≤ T_i ≤ 1000000000)\),表示街道i连接居住点\(U_i\)和\(V_i\),并且经过街道\(i\)需花费\(T_i\)分钟。街道信息不会重复给出。
输出格式:
输出文件仅包含整数T,即最坏情况下Chris的父母需要花费\(T\)分钟才能找到Chris。
我仍未具有将问题很好抽象出模型的能力,所以哪怕大家都说水,我也想到了利用树的直径来贪心的时候,我依旧写爆了这个题。
\(\lmoustache E(C,A)+E(A,B),A,B,C \in G,E(C,A)<E(C,B)\)
\(\rmoustache E(C,B)+E(B,A),A,B,C \in G,E(C,A)>E(C,B)\)
模型即为求解以上的最大值。
我们关注两条链如何分别取到最大值。
对于\(E_1(C,A)\)和\(E_2(C,B)\),我们发现,对任意点\(C\),\(E_1\),\(E_2\)一定是距离它最远和次远的两个点。
这是什么,就是树的直径的两个端点啊。(求解树的直径以及这是为什么可以看看NOIP2007”树网的核”或者SDOI2011”消防”)
此时另一条链恰好不就是取到了自己的最大值?
那么枚举直径外每个点就好了。
code(代码真的丑QAQ·):
#include <cstdio>
#include <cstring>
#define ll long long
const int N=200010;
ll max(ll x,ll y) {return x>y?x:y;}
ll min(ll x,ll y) {return x<y?x:y;}
struct Edge
{
ll next,to,w;
}edge[N*2];
ll read()
{
ll x=0;char c=getchar();
while(c<'0'||c>'9') c=getchar();
while(c>='0'&&c<='9') {x=x*10+c-'0';c=getchar();}
return x;
}
int head[N],cnt=0;
void add(ll u,ll v,ll w)
{
edge[++cnt].next=head[u];edge[cnt].to=v;edge[cnt].w=w;head[u]=cnt;
}
ll n,m;
int used[N];
int l,r;
ll m_max=0;
void f_dfs(ll now,ll ww)
{
used[now]=1;
if(m_max<ww)
{
m_max=ww;
l=now;
}
for(int i=head[now];i;i=edge[i].next)
{
ll v=edge[i].to,w=edge[i].w;
if(!used[v])
f_dfs(v,w+ww);
}
}
ll ge_dfs(ll now)
{
used[now]=1;
ll m_max=0;
for(int i=head[now];i;i=edge[i].next)
{
ll v=edge[i].to,w=edge[i].w;
if(!used[v])
m_max=max(ge_dfs(v)+w,m_max);
}
return m_max;
}
int flag=1;
ll f[N],w0[N],f0[N];
void b_dfs(ll now)
{
used[now]=1;
if(now==r)
flag=0;
for(int i=head[now];i;i=edge[i].next)
{
ll v=edge[i].to,w=edge[i].w;
if(!used[v]&&flag)
{
b_dfs(v);
if(!flag)
{
f[v]=now;
w0[v]=w;
}
}
}
}
ll ans=0;
ll g[N],cnt0=0;
int main()
{
n=read(),m=read();
ll u,v,w;
for(int i=1;i<=m;i++)
{
u=read(),v=read(),w=read();
add(u,v,w);
add(v,u,w);
}
f_dfs(1,0);//求端点
r=l;
m_max=0;
memset(used,0,sizeof(used));
f_dfs(r,0);//求端点
memset(used,0,sizeof(used));
b_dfs(l);//构建链
memset(used,0,sizeof(used));
int now=r;
while(now)
{
used[now]=1;
g[++cnt0]=now;
now=f[now];
}
for(int i=1;i<=cnt0;i++)
f0[i]=f0[i-1]+w0[g[i-1]];
for(int i=1;i<=cnt0;i++)
ans=max(ans,ge_dfs(g[i])+min(f0[i],f0[cnt0]-f0[i]));
printf("%lld\n",ans+f0[cnt0]);
return 0;
}
2018.5.24
洛谷 P4408 逃学的小孩 解题报告的更多相关文章
- 洛谷P4408 逃学的小孩
题目 求树的直径,因为任意两个居住点之间有且只有一条通路,所以这是一棵树. 根据题意父母先从C去A,再去B,或者反过来. 我们一定是要让A到B最大,也要让C到A和B的最小值最大. AB最大一定就是直径 ...
- 洛谷_Cx的故事_解题报告_第四题70
1.并查集求最小生成树 Code: #include <stdio.h> #include <stdlib.h> struct node { long x,y,c; ...
- 洛谷 P2317 [HNOI2005]星际贸易 解题报告
P2317 [HNOI2005]星际贸易 题目描述 输入输出格式 输入格式: 输出格式: 如果可以找到这样的方案,那么输出文件output.txt中包含两个整数X和Y.X表示贸易额,Y表示净利润并且两 ...
- 洛谷 P3802 小魔女帕琪 解题报告
P3802 小魔女帕琪 题目背景 从前有一个聪明的小魔女帕琪,兴趣是狩猎吸血鬼. 帕琪能熟练使用七种属性(金.木.水.火.土.日.月)的魔法,除了能使用这么多种属性魔法外,她还能将两种以上属性组合,从 ...
- 洛谷 P2606 [ZJOI2010]排列计数 解题报告
P2606 [ZJOI2010]排列计数 题目描述 称一个\(1,2,...,N\)的排列\(P_1,P_2...,P_n\)是\(Magic\)的,当且仅当对所以的\(2<=i<=N\) ...
- 洛谷1303 A*B Problem 解题报告
洛谷1303 A*B Problem 本题地址:http://www.luogu.org/problem/show?pid=1303 题目描述 求两数的积. 输入输出格式 输入格式: 两个数 输出格式 ...
- 洛谷 P3084 [USACO13OPEN]照片Photo 解题报告
[USACO13OPEN]照片Photo 题目描述 农夫约翰决定给站在一条线上的\(N(1 \le N \le 200,000)\)头奶牛制作一张全家福照片,\(N\)头奶牛编号\(1\)到\(N\) ...
- 洛谷 P1379 八数码难题 解题报告
P1379 八数码难题 题目描述 在3×3的棋盘上,摆有八个棋子,每个棋子上标有1至8的某一数字.棋盘中留有一个空格,空格用0来表示.空格周围的棋子可以移到空格中.要求解的问题是:给出一种初始布局(初 ...
- NOIP2015 D2T3 洛谷2680 BZOJ4326 运输计划 解题报告
前言:个人认为这是历年NOIP中比较简单的最后一题了,因此将自己的思路与大家分享. 题目大意: 给一棵无根树,给出m条路径.允许将树上的一条边的权值改为0.求m条路径长度最大值的最小值.n,m< ...
随机推荐
- electron 开发实时加载
第一个方式 cnpm install electron-reload --save-dev cnpm install electron-prebuilt --save-dev require('ele ...
- Codeforces Round #481 (Div. 3)
我实在是因为无聊至极来写Div3题解 感觉我主要的作用也就是翻译一下题目 第一次线上打CF的比赛,手速很重要. 这次由于所有题目都是1A,所以罚时还可以. 下面开始讲题 A.Remove Duplic ...
- bitcoin源码解析 - 交易 Transcation (一)
比特币中的交易可谓是比特币的最核心部分.比特币由交易产生,而区块就是用来存储交易的.所以,交易是比特币存在的载体,同时也是比特币中最复杂的部分.交易的运作层层相扣,各个部分缺一不可,十分严密,由此体现 ...
- 洛谷 P4409 [ZJOI2006] 皇帝的烦恼
题目链接-> OVO 题解: 很久没有写博客了,可能是因为最近太颓废了吧. 刚刚考完期末考试,无比期盼早点外出学习,不要面对成绩,害怕. #include <cstdio> #inc ...
- 基于HTML5 WebGL实现 json工控风机叶轮旋转
突然有个想法,如果能把一些用到不同的知识点放到同一个界面上,并且放到一个盒子里,这样我如果要看什么东西就可以很直接显示出来,而且这个盒子一定要能打开.我用HT实现了我的想法,代码一百多行,这么少的代码 ...
- Python_闭包_27
#闭包:嵌套函数,内部函数 并且必须调用外部函数的变量 def outer(): a = 1 def inner(): print(a) inner() print(inner.__closure__ ...
- js格式化时间
转自:https://blog.csdn.net/u010964869/article/details/51095827 显示格式为:yyyy-mm-dd hh:mi:ss function form ...
- Final 个人最终作业。
1.对软件工程M1/M2做一个总结 在M1阶段,我在C705组.M1阶段我与黄漠源同学结对,一起完成提取关键词算法的优化.最初我们一起测试提取关键词算法功能的实现效果,随后我主要负责从网络上搜寻并整理 ...
- BugPhobia发布篇章:学霸在线系统测试报告
0x00 :测试报告版本管理 版本号 具体细节 修订时间 V 1.0 整理第一轮迭代用户管理和登陆注册的功能性验证测试,预计将继续网页对浏览器版本的兼容性测试 2015/11/12 V1.0.1 整理 ...
- 《面向对象程序设计》c++第五次作业___calculator plus plus
c++第五次作业 Calculator plusplus 代码传送门 PS:这次作业仍然orz感谢一位同学与一位学长的windows帮助,同时再次吐槽作业对Mac系统用户的不友好.(没朋友千万别用Ma ...