[Nowcoder 217042] CCA subtree

CCA subtree

Title link: nowcoder 217042

To Niu Ke:

——>Click me to jump<——

General idea

There is a tree with dot weights, the root node is 1 11 .
You have to choose two points, they will not be the ancestor of the other, and then you have to maximize the sum of their subtree points.
If two points cannot be selected, output themError.

Ideas

We can think that this question should be a tree DP.

Consider the point weight and qi q_i of the subtree of a certain point DP firstqi, And then you can think of using such a method.
We have each point in the subtree of a certain point in DP xxx 'sqx q_xqxMaximum value big _ soni big\_son_ibig_soni.
Then we consider enumerating the nearest common ancestors of the two points you selected, and then put the big _ son big\_son of its subtreeAdd the two largest values ​​of b i g _ s o n to get the maximum value that the answer can have when this point is the nearest common ancestor.

Then you can take all of them to a maximum value and that's it.

Code

#include<cstdio>
#include<iostream>
#define ll long long

using namespace std;

struct node {
    
    
	int to, nxt;
}e[400001];
int n, a[200001], x, y;
int KK, le[200001], maxn_dep;
ll ans, big_son[200001], sum[200001];

void add(int x, int y) {
    
    
	e[++KK] = (node){
    
    y, le[x]}; le[x] = KK; 
}

void dfs(int now, int father, int dep) {
    
    
	maxn_dep = max(maxn_dep, dep);
	big_son[now] = -0x3f3f3f3f3f3f3f3f;
	sum[now] = a[now];
	
	ll maxn = -0x3f3f3f3f3f3f3f3f, maxn2 = -0x3f3f3f3f3f3f3f3f;
	for (int i = le[now]; i; i = e[i].nxt)
		if (e[i].to != father) {
    
    
			dfs(e[i].to, now, dep + 1);
			big_son[now] = max(big_son[now], big_son[e[i].to]);
			sum[now] += sum[e[i].to];
			
			if (big_son[e[i].to] > maxn) {
    
    
				maxn2 = maxn;
				maxn = big_son[e[i].to];
			}
			else if (big_son[e[i].to] > maxn2) maxn2 = big_son[e[i].to];
		}
	
	big_son[now] = max(big_son[now], sum[now]);
	
	ans = max(ans, maxn + maxn2);
}

int main() {
    
    
	ans = -0x3f3f3f3f3f3f3f3f; 
	
	scanf("%d", &n);
	for (int i = 1; i <= n; i++) scanf("%d", &a[i]);
	
	for (int i = 1; i < n; i++) {
    
    
		scanf("%d %d", &x, &y);
		add(x, y);
		add(y, x);
	}
	
	dfs(1, 0, 1);
	
	if (maxn_dep == n) printf("Error");
		else printf("%lld", ans);
	
	return 0;
}

Guess you like

Origin blog.csdn.net/weixin_43346722/article/details/115219563