hihocoder 1881 特殊任务

时间限制:10000ms

单点时限:1000ms

内存限制:256MB

描述

H公司一共有N名员工,编号1~N,其中CEO是1号员工。除了CEO之外,其他员工都有唯一的直接上司,所以N名员工上下级关系恰好形成了一棵树形结构。  

我们知道每一名员工向H公司的代码库贡献了多少行代码。具体来说,第i名员工贡献了Ai行代码。

现在有一项特殊的任务需要2名员工完成,这两名员工需要满足:

1. 其中一名是另一名的直接或者间接上司

2. 两人贡献代码行数的差值越大越好

请你在所有员工中找出符合条件的2人,输出他们代码行数的差值。

输入

第一行包含一个整数N。

第二行包含N个整数A1, A2, ... AN。  

以下N-1行每行包含一个整数,依次是P2, P3, ... PN,其中Pi代表第i名员工的上司编号。  

对于30%的数据,1 ≤ N ≤ 1000

对于100%的数据,1 ≤ N ≤ 100000, 0 ≤ Ai ≤ 100000, 1 ≤ Pi ≤ N

输出

一个整数代表答案

题解:对这个关系进行建树,只需要保存每个人有多少个下级就可以了,也可以全部建完,然后从1开始进行DFS不断更新最大值和最小值,我们所求的答案一定是,当前节点对应的值与最大值与最小值的差的一个,这里我使用了pair保存最大值与最小值。

#include<iostream>
#include<algorithm>
#include<stdio.h>
#include<string.h>
#include<vector>
using namespace std;
int a[100005];
int c[100005];
vector<int>v[100005];
int m1, m2;
pair<int,int> dfs(int cur)
{
	int len = v[cur].size();
	int tmp1, tmp2;
	tmp1 = tmp2 = a[cur];
	for (int i = 0; i < len; i++)
	{
		int vv = v[cur][i];
		pair<int, int> mm = dfs(vv);
		tmp1= min(tmp1, mm.first);
		tmp2= max(tmp2, mm.second);
		m1 = max(m1, abs(mm.second - a[cur]));
		m1 = max(m1, abs(mm.first - a[cur]));
	}
	return make_pair(tmp1, tmp2);
}

int main()
{
	int n;
	cin >> n;
	for (int i = 1; i <= n; i++)
		cin >> a[i];
	int t;
	for (int i = 2; i <= n; i++)
	{
		cin >> t;
		v[t].push_back(i);
	}
	dfs(1);
	cout << m1 << endl;
	return 0;
}

猜你喜欢

转载自blog.csdn.net/KXL5180/article/details/84727208
今日推荐