洛谷P3627 APIO2009 搶掠計畫

2022-05-23 21:54:10 字數 1393 閱讀 1522

題目大意:給你一張$n(n\leqslant5\times10^5)$個點$m(m\leqslant5\times10^5)$條邊的有向圖,有點權,給你起點和一些可能的終點。問從起點開始,到任意乙個終點經過的點權和的最大值是多少。

題解:先把有向圖縮點,然後從起點跑最長路,對每個終點取個最大值即可

卡點:求最長路寫了$dijkstra$,然後死活調不出。

c++ code:

#include #include #include #include namespace __io 

}using __io::read;

const int maxn = 500010, maxm = 500010;

int n, m;

int w[maxn], w[maxn];

namespace graph e[maxm];

inline void addedge(int a, int b) ; head[a] = cnt;

} int dfn[maxn], low[maxn], idx;

int s[maxn], top, bel[maxn], scc;

bool ins[maxn];

void tarjan(int u) else if (ins[v]) low[u] = std::min(low[u], dfn[v]);

} if (dfn[u] == low[u]) while (v != u);

} }}int head[maxn], cnt;

struct edge e[maxm];

inline void addedge(int a, int b) ; head[a] = cnt;

}using graph::scc;

using graph::bel;

std::queueq;

int dis[maxn];

bool inq[maxn];

void spfa(int s)

} }}int s, ans;

int main()

for (int i = 1; i <= n; ++i) w[i] = read();

s = read();

graph::tarjan(s);

for (int i = 1, u, v; i <= m; ++i)

spfa(bel[s]);

for (int i = read(), x; i; --i) ans = std::max(ans, dis[bel[x = read()]]);

printf("%d\n", ans);

return 0;

}

P3627 APIO2009 搶掠計畫

題目描述 siruseri 城中的道路都是單向的。不同的道路由路口連線。按照法律的規定,在每個路口都設立了乙個 siruseri 銀行的 atm 取款機。令人奇怪的是,siruseri 的酒吧也都設在路口,雖然並不是每個路口都設有酒吧。banditji 計畫實施 siruseri 有史以來最驚天動地...

P3627 APIO2009 搶掠計畫

p3627 apio2009 搶掠計畫 tarjan縮點 最短 最長 路 顯然的縮點.在縮點時,順便維護每個強連通分量的總權值 縮完點按照慣例建個新圖 然後跑一遍spfa最長路,列舉每個有酒吧的點即可 但是我為什麼會搞dp呢.dp 81pts 這麼顯然的最長路,為什麼會搞dp呢.怕不是被dp題毒害了...

P3627 APIO2009 搶掠計畫

傳送門 演算法 tarjan dp 顯然縮點後的圖是乙個dag dag上搞dp是基本操作啊 按拓撲序搞一波dp就好了 設 f i 表示從起點搶劫到 dag 上的點 i 時能得到的最多的錢 那麼 f i max f i f j sval i j 有一條邊指向 i sval i 表示dag上點 i 的錢...