求助缩点,萌新调了一周了呜呜
查看原帖
求助缩点,萌新调了一周了呜呜
220426
血色黄昏楼主2020/10/24 10:45
#include<bits/stdc++.h>
using namespace std;
int n, m, val[100010], dfn[100010], low[100010], cnt=0, x, y, sd[100010], dp[100010], ans = 0, geshu=0;
bool instack[100010];
vector<int>l[100010];
vector<int>news[100010];
stack<int>s;
int DP(int x)
{
	if(dp[x] > 0)return dp[x];
	for (int i = 0;i < news[x].size();i ++)dp[x] = max(dp[x],DP(news[x][i]) + val[x]);
	return dp[x];
}
void tarjan(int u)
{
	low[u]=dfn[u]=++cnt;
	instack[u] = true;
	s.push(u);
	for(int i = 0;i < l[u].size();i ++)
	{
		int v = l[u][i];
		if(!dfn[v])
		{
			tarjan(v);
			low[u] = min(low[u], low[v]);
		}
		else if(instack[v])
		{
			low[u] = min(low[u], dfn[v]);
		}
	}
	if(dfn[u] == low[u])
	{
		geshu++;
		int qaq;
		while(!s.empty())
		{
			qaq = s.top();
			s.pop();
			instack[qaq] = false;
			sd[qaq] = u;
			if(qaq == u)break;
			val[u] += val[qaq];
		}
	}
}

int main(){
    memset(dp, 0, sizeof(dp));
    memset(dfn, 0, sizeof(dfn));
    memset(low, 0, sizeof(low));
    memset(instack, false, sizeof(instack));
    scanf("%d%d",&n,&m);
	for (int i=1;i<=n;i++)scanf("%d",&val[i]);
	
	for (int i=1;i<=m;i++)
	{
		int u,v;
		scanf("%d%d",&u,&v);
		l[u].push_back(v);
	}
    for(int i = 1;i <= n;i ++)if(!dfn[i])tarjan(i);
    for(int i = 1;i <= n ;i ++)cout<<dfn[i]<<" "<<low[i]<<endl;
	if(geshu == 1)
	{
		for(int i = 1;i <= n;i ++)ans = max(ans, val[i]);
		cout<<ans<<endl;
		return 0;
	}
    for(int i = 1;i <= n;i ++)
    {
    	for(int j = 0;j < l[i].size();j ++)
    	{
    		if(sd[l[i][j]] == sd[i])continue;
    		news[sd[i]].push_back(sd[l[i][j]]);
		}
	}
	for(int i = 1;i <= n;i ++)if(!dp[i])DP(i);
	for(int i = 1;i <= n;i ++)ans = max(ans, dp[i]);
	cout<<ans<<endl;
    return 0;
}

和题解对了一下应该是因为tarjan时有些点dfn和low的输出不同,求神仙指正qwq

2020/10/24 10:45
加载中...