WA 50 pts求调,输出结果比标准答案小
查看原帖
WA 50 pts求调,输出结果比标准答案小
479448
fire_and_sweets楼主2024/6/24 16:17

Code:

#include <bits/stdc++.h>
using namespace std;
#define int long long

const int N = 1000010, M = 2 * N;

int n, a[N], res, f[N][2], s1, f1, s2, f2;
bool st[N];
int h[N], e[M], ne[M], idx = 1;
vector<int> path, s;

void add(int a, int b)
{
	e[idx] = b, ne[idx] = h[a], h[a] = idx ++ ;
}

void dfs(int u, int father)
{
	if (st[u])
	{
		s1 = path.back();
		s2 = path[(int)path.size() - 2];
		return;
	}
	else s.push_back(u);
	st[u] = true;
	for (int i = h[u]; ~i; i = ne[i]) 
	{
		int j = e[i];
		if (j == father) continue;
		path.push_back(j);
		dfs(j, u);
		if (s1 != -1 || s2 != -1) return;
	}
	path.pop_back();
}

void dp(int u, int father)
{
	st[u] = true;
	f[u][0] = 0;
	f[u][1] = a[u];
	for (int i = h[u]; ~i; i = ne[i])
	{
		int j = e[i];
		if (j == father) continue;
		if (u == s1 && j == s2) continue;
//cout << u << ">> " << j << endl;
		if (u == s2 && j == s1) continue;
//		cout << u << " -> " << j << endl;
		dp(j, u);
		f[u][0] += max(f[j][0], f[j][1]);
		f[u][1] += f[j][0];
	}
	f[s1][f1] = f[s2][f2] = 0;
}

void work(int x)
{
	int maxn = 0;
	path.clear(); s.clear();
	path.push_back(x);
	s1 = s2 = -1;
	dfs(x, -1);
//	cout << s.size() << endl;
 	if (s1 != -1 && s2 != -1 && s.size() == 2)
	{
		res += max(a[s1], a[s2]);
		return;
	}
//	cout << s1 << " " << s2 << endl;
	memset(f, 0, sizeof f);
	f1 = f2 = 1; dp(x, -1);
	maxn = max(maxn, max(f[x][0], f[x][1]));
	f1 = 1, f2 = 0; dp(x, -1);
	maxn = max(maxn, max(f[x][0], f[x][1]));
	f1 = 0, f2 = 1; dp(x, -1);
	maxn = max(maxn, max(f[x][0], f[x][1]));
	res += maxn;
}

signed main()
{
	memset(h, -1, sizeof h);
	cin >> n;
	for (int i = 1; i <= n; i ++ )
	{
		int x;
		cin >> a[i] >> x;
		add(i, x), add(x, i);
	}
	for (int i = 1; i <= n; i ++ )
		if (!st[i]) work(i);
	cout << res << endl;
	return 0;
}
2024/6/24 16:17
加载中...