【问题描述】
n 个小朋友在玩传球。 小朋友们用 1 到 n 的正整数编号。 每个小朋友有一个固定的传球
对象,第 i 个小朋友在接到球后会将球传给第 ai个小朋友, 并且第 i 个小朋友与第 ai个小朋
友之间的距离为 di。
一次传球接力是这样进行的:由一个小朋友发球,将球传给他的传球对象,之后接到球
的小朋友再将球传给自己的传球对象,如此传球若干次后停止。 期间,包括发球者在内,每
个小朋友至多只能拿到球一次。 一次传球接力的总距离是每次传球的距离的总和。
小朋友们想进行一次总距离最长的传球接力,现在需要你帮助他们求出满足上述要求的
传球接力的最长总距离。
【输入】
输入的第 1 行包含 1 个整数 n。
接下来的 n 行,第 i 行包含两个整数 ai 和 di,意义如题目中所述, 两个数间用一个空格
隔开。
【输出】
输出包含 1 个数, 表示传球接力总距离的最大值。
【输入输出样例 1】

pass.in pass.out
5
2 1
3 2
4 1
2 3
3 3
7

见选手目录下的 pass / pass1.in 与 pass / pass1.out
【输入输出样例 1 说明】
由第 5 个小朋友发球, 传给第 3 个小朋友,再传给第 4 个小朋友,总距离为 3+1+3=7
【数据规模与约定】
对于 50%的数据, n≤1,000
对于 100%的数据, n≤500,000, 1≤ai≤n, ai≠i, 1≤di≤10,000

分析:对图的特征一定要搞清楚,比如n个点n-1条边就是树,n个点n条边就是树套环,每个点出度为1就是很多链和环的结合体.为了走的最远,肯定要从入度为0的点出发,走到环上,顺着环走一遍.每次都模拟这样走一遍效率不高,因为一个环会被多次使用,所以可以先把环的长度给预处理出来,再把每个入度为0的点到环上的距离利用树形dp给算出来,因为最后不能回到自身嘛,枚举一下断点就可以了.

因为图可能不是连通的,会有多个环,所以要把所有的点都给处理到位.

暴力50分:

#include <map>
#include <cmath>
#include <queue>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm> using namespace std; const int maxn = ; int n, head[maxn], maxx,to[maxn], nextt[maxn], w[maxn], tot = , ans;
bool vis[];
long long sum; void add(int x, int y, int z)
{
w[tot] = z;
to[tot] = y;
nextt[tot] = head[x];
head[x] = tot++;
} void dfs(int x, int d)
{
vis[x] = ;
ans = max(ans, d);
for (int i = head[x]; i; i = nextt[i])
{
int v = to[i];
if (!vis[v])
dfs(v, d + w[i]);
}
} int main()
{
scanf("%d", &n);
for (int i = ; i <= n; i++)
{
int a, d;
scanf("%d%d", &a, &d);
add(i, a, d);
}for (int i = ; i <= n; i++)
{
dfs(i, );
memset(vis, , sizeof(vis));
}
printf("%d\n", ans);return ;
}

正解:

#include <queue>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm> using namespace std; typedef long long ll; const int maxn = ;
ll n, a[maxn], d[maxn], du[maxn], f[maxn], sum = , ans, pre[maxn], cnt, p[maxn];
bool vis[maxn]; int main()
{
scanf("%lld", &n);
for (int i = ; i <= n; i++)
{
scanf("%lld%lld", &a[i], &d[i]);
du[a[i]]++;
}
queue <ll> q;
for (int i = ; i <= n; i++)
if (!du[i])
q.push(i);
while (!q.empty())
{
ll u = q.front();
q.pop();
ll v = a[u];
f[v] = max(f[v], f[u] + d[u]);
if (--du[v] == )
q.push(v);
}
for (int i = ; i <= n; i++)
if (du[i] && !vis[i])
{
ll k = i;
sum = ;
do
{
vis[k] = ;
p[++cnt] = k;
pre[a[k]] = d[k];
sum += d[k];
k = a[k];
} while (k != i);
for (int j = ; j <= cnt; j++)
ans = max(ans, sum + f[p[j]] - pre[p[j]]);
}
printf("%lld\n",ans); return ;
}

noip模拟赛 传球接力的更多相关文章

  1. NOIP模拟赛20161022

    NOIP模拟赛2016-10-22 题目名 东风谷早苗 西行寺幽幽子 琪露诺 上白泽慧音 源文件 robot.cpp/c/pas spring.cpp/c/pas iceroad.cpp/c/pas ...

  2. contesthunter暑假NOIP模拟赛第一场题解

    contesthunter暑假NOIP模拟赛#1题解: 第一题:杯具大派送 水题.枚举A,B的公约数即可. #include <algorithm> #include <cmath& ...

  3. NOIP模拟赛 by hzwer

    2015年10月04日NOIP模拟赛 by hzwer    (这是小奇=> 小奇挖矿2(mining) [题目背景] 小奇飞船的钻头开启了无限耐久+精准采集模式!这次它要将原矿运到泛光之源的矿 ...

  4. 大家AK杯 灰天飞雁NOIP模拟赛题解/数据/标程

    数据 http://files.cnblogs.com/htfy/data.zip 简要题解 桌球碰撞 纯模拟,注意一开始就在袋口和v=0的情况.v和坐标可以是小数.为保险起见最好用extended/ ...

  5. 队爷的讲学计划 CH Round #59 - OrzCC杯NOIP模拟赛day1

    题目:http://ch.ezoj.tk/contest/CH%20Round%20%2359%20-%20OrzCC杯NOIP模拟赛day1/队爷的讲学计划 题解:刚开始理解题意理解了好半天,然后发 ...

  6. 队爷的Au Plan CH Round #59 - OrzCC杯NOIP模拟赛day1

    题目:http://ch.ezoj.tk/contest/CH%20Round%20%2359%20-%20OrzCC杯NOIP模拟赛day1/队爷的Au%20Plan 题解:看了题之后觉得肯定是DP ...

  7. 队爷的新书 CH Round #59 - OrzCC杯NOIP模拟赛day1

    题目:http://ch.ezoj.tk/contest/CH%20Round%20%2359%20-%20OrzCC杯NOIP模拟赛day1/队爷的新书 题解:看到这题就想到了 poetize 的封 ...

  8. CH Round #58 - OrzCC杯noip模拟赛day2

    A:颜色问题 题目:http://ch.ezoj.tk/contest/CH%20Round%20%2358%20-%20OrzCC杯noip模拟赛day2/颜色问题 题解:算一下每个仆人到它的目的地 ...

  9. CH Round #52 - Thinking Bear #1 (NOIP模拟赛)

    A.拆地毯 题目:http://www.contesthunter.org/contest/CH%20Round%20%2352%20-%20Thinking%20Bear%20%231%20(NOI ...

随机推荐

  1. Gamma阶段测试计划

    前言 点击这一链接访问公课网(笨拙软件工程组). 一.Alpha阶段场景测试 1.1 鹿丸:无欲无求大三学生 保研无望 不在乎给分 只想选择干货多的课程 充实自己 需求和目标:了解各专业课程的授课内容 ...

  2. Apache Kafka官方文档翻译(原创)

    Apache Kafka是一个分布式流平台.准确的说是什么意思呢?我们认为流平台具有三种关键能力: 1.让你对数据流进行发布订阅.因此他很像一个消息队列和企业级消息系统. 2.让你以高容错的方式存储数 ...

  3. GIT学习之路第五天 分支管理

    本文参考廖雪峰老师的博客进行总结,完整学习请转廖雪峰博客 5.1创建与合并分支 首先创建dev分支,然后切换dev分支 $git checkout -b dev(包含创建并切换) 等价于<-&g ...

  4. CircuitBreaker design pattern---reference

    It's common for software systems to make remote calls to software running in different processes, pr ...

  5. servlet下的request&&response

    request的方法     *获取请求方式: request.getMethod();     * 获取ip地址的方法 request.getRemoteAddr();     * 获得用户清气的路 ...

  6. 安装linux mint 18.3 后要做的

    使用u盘安装的linux mint 18.3,安装过程基本顺利 发现在安装过程中使用中文语言的话会使得下载附加软件的速度快很多 安装完成之后要做的事情有: 1.字体 默认的楷体字比较难看,在软件管理器 ...

  7. 神奇的Object.defineProperty

    vue.js和avalon.js 都是通过它实现双向绑定的. 对象是由多个名/值对组成的无序的集合.对象中每个属性对应任意类型的值.定义对象可以使用构造函数或字面量的形式: var obj={}; o ...

  8. 用Python利用pyFirmata控制Arduino实现Blink

    2018-03-2809:20:44 arduino中有相应的库 1.安装pyFirmata包 pip install pyFirmata 在python2.7或python3.X下都可以执行. py ...

  9. Selenium基于Python web自动化测试框架 -- PO

    关于selenium测试框架首先想到的就是PO模型,简单说下PO模型 PO模型的概念和理解: PO就是一个设计思想,将代码以页面为单位进行组织,针对这个页面上的所有信息.相关操作都放到一个类中,从而使 ...

  10. 4星|《OKR工作法》:关注公司的真正目标,以周为单位做计划和考核

    本书篇幅比较小,两个小时就可以看完.主要内容讲OKR工作法的基本概念,然后用一个虚拟的创业公司的创业故事来演示实施OKR过程中可能遇到的问题.OKR给创业带来的好处. OKR工作法相对来说是比较简单的 ...