题意其实就是给你一个有向图 但是每个SCC里面的点数目不超过5 求最长路

首先暴力把每个SCC里的每个点的最长路跑出来 然后拓扑排序dp

#include<bits/stdc++.h>
#define MOD 1000000007
using namespace std;
typedef long long ll;
const int N = 1000005;
vector<int> g[2 * N], g2[N];
int dfn[N], low[N], bel[N], dfc, scc;
bool inst[N];
int scs[N], *sct = scs;
void scc_clr(int n) {
        fill(dfn + 1, dfn + n + 1, 0);
}
int dfs_scc(int u) {
        *sct++ = u;
        inst[u] = 1;
        dfn[u] = low[u] = ++dfc;
        for (int v : g[u]) {
                if (!dfn[v]) {
                        low[u] = min(low[u], dfs_scc(v));
                } else if (inst[v]) {
                        low[u] = min(low[u], dfn[v]);
                }
        }
        if (dfn[u] == low[u])
                for (++scc; *sct != u; --sct) {
                        bel[sct[-1]] = scc, inst[sct[-1]] = 0;
                }
        return low[u];
}
bool vis[N];
int dp[N], du[N];
int ans = 0;
queue<int> que;
int doit(int x, int y, bool f) {
        if (vis[x]) {
                return 0;
        }
        if (bel[x] != y) {
                if (f) {
                        return dp[x];
                } else {
                        return 0;
                }
        }
        int anser = 1;
        vis[x] = 1;
        for (int v : g[x]) {
                anser = max(anser, doit(v, y, f) + 1);
        }
        vis[x] = 0;
        dp[x] = max(dp[x], anser);
        ans = max(ans, dp[x]);
        return anser;
}
int main () {
        int n, m;
        scanf("%d %d", &n, &m);
        for (int i = 1; i <= m; i++) {
                int u, v;
                scanf("%d %d", &u, &v);
                g[u].push_back(v);
        }
        for (int i = 1; i <= n; i++)
                if (!dfn[i]) {
                        dfs_scc(i);
                }
        for (int i = 1; i <= n; i++) {
                g[bel[i] + n].push_back(i);
                for (int v : g[i]) {
                        if (bel[v] != bel[i]) {
                                g2[bel[v]].push_back(bel[i]);
                                du[bel[i]]++;
                        }
                }
        }
        for (int i = 1; i <= scc; i++) {
                if (du[i] == 0) {
                        que.push(i);
                }
                for (int v : g[i + n]) {
                        doit(v, i, 0);
                }
        }
        while (que.size()) {
                int x = que.front();
                que.pop();
                for (int v : g[x + n]) {
                        doit(v, x, 1);
                }
                for (int v : g2[x]) {
                        du[v]--;
                        if (du[v] == 0) {
                                que.push(v);
                        }
                }
        }
        cout << ans << endl;
}
01-14 03:30