bzoj1924: [Sdoi2010]所驼门王的宝藏
来源:互联网 发布:linux fm驱动 编辑:程序博客网 时间:2024/05/21 06:57
传送门
我们首先可以用O(NlogN)的时间建出来所有的边。
然后我们大力tarjan求联通块
之后大力拓扑排序一发就可以了。
#include<cstdio> #include<iostream>#include<cstdlib>#include<cmath>#include<cstring>#include<algorithm>#include<vector>#include<map>#define N 100005#define M 1000005using namespace std;const int xxx[8][2]={{-1,-1},{-1,0},{-1,1},{0,-1},{0,1},{1,-1},{1,0},{1,1}};int head[N],head2[N],x[N],y[N],z[N],co[N];int dfn[N],low[N],num[N],st[N],inq[N],mark[N],sum[N];vector<int> a[M],b[M];map<int,int> mp[M];struct edge{int to,next;}e[M],ed[M];int K,n,m,tot,top,color,tim,ans;inline int read(){ int x=0; char ch=getchar(); for (;ch<'0'||ch>'9';ch=getchar()); for (;ch>='0'&&ch<='9';ch=getchar()) x=x*10-48+ch; return x; }void ins(int x,int y){ if (x==y) return; e[++tot].to=y; e[tot].next=head[x]; head[x]=tot;}void ins2(int x,int y){ if (x==y) return; ed[++tot].to=y; ed[tot].next=head2[x]; head2[x]=tot;}void build(){ int p,t; for (int i=1;i<=n;i++){ p=0; t=a[i].size(); for (int j=0;j<t;j++) if (z[a[i][j]]==1){p=a[i][j]; break;} if (!p) continue; for (int j=0;j<t;j++){ ins(p,a[i][j]); if (z[a[i][j]]==1) ins(a[i][j],p); } } for (int i=1;i<=m;i++){ p=0; t=b[i].size(); for (int j=0;j<t;j++) if (z[b[i][j]]==2){p=b[i][j]; break;} if (!p) continue; for (int j=0;j<t;j++){ ins(p,b[i][j]); if (z[b[i][j]]==2) ins(b[i][j],p); } } for (int i=1;i<=K;i++) if (z[i]==3) for (int j=0;j<8;j++){ t=mp[x[i]+xxx[j][0]][y[i]+xxx[j][1]]; if (t) ins(i,t); }}void tarjan(int x){ dfn[x]=low[x]=++tim; inq[x]=1; st[++top]=x; for (int i=head[x];i;i=e[i].next) if (!dfn[e[i].to]){ tarjan(e[i].to); low[x]=min(low[x],low[e[i].to]); } else if (inq[e[i].to]) low[x]=min(low[x],dfn[e[i].to]); if (dfn[x]==low[x]){ int xx=0; color++; while (xx!=x){ xx=st[top--]; co[xx]=color; inq[xx]=0; num[color]++; } }}void rebuild(){ tot=0; for (int i=1;i<=K;i++) for (int j=head[i];j;j=e[j].next) if (co[i]!=co[e[j].to]) ins2(co[i],co[e[j].to]);}void dp(int x){ mark[x]=1; for (int i=head2[x];i;i=ed[i].next){ if (!mark[ed[i].to]) dp(ed[i].to); sum[x]=max(sum[x],sum[ed[i].to]); } sum[x]+=num[x]; ans=max(ans,sum[x]);}int main(){ K=read(); n=read(); m=read(); for (int i=1;i<=K;i++){ x[i]=read(); y[i]=read(); z[i]=read(); mp[x[i]][y[i]]=i; a[x[i]].push_back(i); b[y[i]].push_back(i); } build(); for (int i=1;i<=K;i++) if (!dfn[i]) tarjan(i); rebuild(); for (int i=1;i<=color;i++) if (!mark[i]) dp(i); printf("%d",ans); }
阅读全文
0 0
- 【SDOI2010】【BZOJ1924】所驼门王的宝藏
- BZOJ1924: [Sdoi2010]所驼门王的宝藏
- BZOJ1924: [Sdoi2010]所驼门王的宝藏
- bzoj1924 [Sdoi2010]所驼门王的宝藏
- bzoj1924: [Sdoi2010]所驼门王的宝藏
- 【BZOJ1924】【SDOI2010】所驼门王的宝藏
- 【bzoj1924】【SDOI2010】所驼门王的宝藏
- [BZOJ1924][SDOI2010]所驼门王的宝藏(Tarjan+拓扑排序)
- 【bzoj1924】[Sdoi2010]所驼门王的宝藏(tarjan+STL+dp)
- bzoj1924 所驼门王的宝藏
- bzoj1924 [Sdoi2010]所驼门王的宝藏(tarjan缩点+拓扑排序+dp)
- bzoj1924 所驼门王的宝藏 有向图最长链
- 【codevs2131】【BZOJ1924】所驼门王的宝藏,tarjan+拓扑DP
- 1924: [Sdoi2010]所驼门王的宝藏
- 1924: [Sdoi2010]所驼门王的宝藏
- 省选专练SDOI2010所驼门王的宝藏
- [BZOJ]1924: [Sdoi2010]所驼门王的宝藏 强连通+DP
- [SDOI2010]所驼门王的宝藏 --tarjan缩点+最长路
- vxWorks中sysClkRateGet()返回系统时钟详解
- C++ Sort函数
- 银行系统
- TinyXml解析代码
- Android Studio 2.3 上面加NDK的支持
- bzoj1924: [Sdoi2010]所驼门王的宝藏
- 华为笔试题1
- 2017暑假集训 div1 线段树(1)
- [bzoj3282]Tree Link-Cut-Tree
- 程序、任务、进程和线程的联系与区别
- 继承的相关知识
- 使用Java 8 的日期和时间Api
- spring AOP---【小白系列】0基础到熟练应用spring框架(三)
- 洛谷P1008 三连击