POJ 3592 Instantaneous Transference(建图+缩点)
2012-09-02 10:57
239 查看
题意:在n*m 的图上只能向右4和向下走,问最多可以那都拿走多少矿石;# 表示不能到达该点,*表示该点可以传送的其他的点。
该图是一个有向图,可以传送到前面的点,所以可能出现环,因此可以用联通图缩点。然后从(0,0)点开始找最长的路劲。
做这题出现了各种错,无语了。
一组数据:
1
4 4
111*
1121
1*11
1111
2 0
0 2
答案:10
该图是一个有向图,可以传送到前面的点,所以可能出现环,因此可以用联通图缩点。然后从(0,0)点开始找最长的路劲。
做这题出现了各种错,无语了。
一组数据:
1
4 4
111*
1121
1*11
1111
2 0
0 2
答案:10
#include <iostream> #include <cstdio> #include <cstring> #include <algorithm> #include <cmath> #include <queue> #include <stack> using namespace std; const int N = 49; const int M = 1609; int n,m; char map ; struct LT{ int to,nex; } L[M<<2],NL[M<<2]; int F[M],cnt; int NF[M],ncnt; void add(int f,int t) { L[cnt].nex = F[f]; L[cnt].to = t; F[f] = cnt++; } int val[M]; void init() { scanf("%d%d",&n,&m); memset(F,0,sizeof(F)); cnt = 1; for(int i=0;i<n;i++) { scanf("%s",map[i]); for(int j=0;j<m;j++) { if(map[i][j]>='0'&&map[i][j]<='9') val[i*m+j] = map[i][j] -'0'; else val[i*m+j] = 0; if(map[i][j]=='#') continue; if(i>0&&map[i-1][j]!='#') add((i-1)*m+j,i*m+j); if(j>0&&map[i][j-1]!='#') add(i*m+j-1,i*m+j); } } int x,y; for(int i=0;i<n;i++) for(int j=0;j<m;j++) if(map[i][j]=='*') { scanf("%d%d",&x,&y); add(i*m+j,x*m+y); } } int dfn[M],low[M],col[M],color,ind; bool post[M]; stack<int> S; void tdfs(int k) { low[k] = dfn[k] = ind++; post[k] = true;S.push(k); for(int i=F[k];i;i=L[i].nex) { int to = L[i].to; if(!dfn[to]) { tdfs(to); low[k] = min(low[k],low[to]); }else if(post[to]&&low[k]>dfn[to]) low[k] = dfn[to]; } if(low[k]==dfn[k]) { color++;int i; for(i=S.top(),S.pop();i!=k;i=S.top(),S.pop()) { col[i] = color;post[i] = false; } col[k] = color;post[k] = false; } } void tarjan() { for(int i=0;i<(n*m);i++) dfn[i] = low[i] = 0,post[i] = false; ind = 1,color=0;while(!S.empty())S.pop(); tdfs(0); } int nval[M]; void nadd(int f,int t) { NL[ncnt].nex = NF[f]; NL[ncnt].to = t; NF[f] = ncnt++; } int dp[M],ans; int visit[M]; void dfs(int k,int s) { if(visit[k]) return ; s+=nval[k]; if(dp[k]>s) return ; visit[k] = true; dp[k] = s; ans = max(ans,s); for(int i=NF[k];i;i=NL[i].nex) { int to = NL[i].to; dfs(to,s); } visit[k] = false; } void solve() { memset(col,0,sizeof(col)); tarjan(); memset(NF,0,sizeof(NF));ncnt = 1; memset(nval,0,sizeof(nval)); for(int i=0;i<(n*m);i++) { nval[col[i]] += val[i]; for(int j=F[i];j;j=L[j].nex) { int to = L[j].to; nadd(col[i],col[to]); } } ans = 0; memset(dp,0,sizeof(dp)); memset(visit,false,sizeof(visit)); dfs(col[0],0); printf("%d\n",ans); } int main() { freopen("in.txt","r",stdin); int cas; scanf("%d",&cas); while(cas--) { init(); solve(); } return 0; }
相关文章推荐
- poj 3592 Instantaneous Transference
- POJ 3592 Instantaneous Transference 缩点构图求最长路
- Poj 3592 Instantaneous Transference
- POJ 3592 Instantaneous Transference
- POJ 3592--Instantaneous Transference【SCC缩点新建图 && SPFA求最长路 && 经典】
- POJ -- 3592 Instantaneous Transference (强连通+记忆化搜索)
- POJ 3592 强连通缩点+spfa最长路
- POJ 3592 Instantaneous Transference
- poj 3592 Instantaneous Transference 【SCC +缩点 + SPFA】
- poj 3592 Instantaneous Transference(强连通+最长路)
- poj 3592 Instantaneous Transference(强连通分量)
- POJ 3592 Instantaneous Transference
- poj 3592 Instantaneous Transference 强连通图 缩点 再求最长路
- poj 3592 Instantaneous Transference
- POJ 3592 Instantaneous Transference 图论算法tarjan+spfa
- POJ 3592 Instantaneous Transference 强连通缩点+spfa最长路
- poj 3592 Instantaneous Transference
- POJ 3592 Instantaneous Transference
- POJ 3592 缩点+拓扑排序+最长路
- POJ 3592 Instantaneous Transference 强连通分量+缩点+DP