转载请注明出处: http://www.cnblogs.com/fraud/ ——by fraud
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 1589 Accepted Submission(s): 587
题意:
给出一个序列,问LIS的长度以及长度为LIS长度的不相交的上升序列的个数
分析:
n2 求出LIS,同时维护好信息,然后构图。
若dp[i]=1,则由源点向该点连一条容量为1的边,若dp[i]=dp[j]+1,则由j向i连一条容量为1的边,若dp[i]=LIS的长度,则由i向汇点连一条容量为1的边。
注意要拆点。虽然这题数据比较水,不拆点也能过。
1 //##################### 2 //Author:fraud 3 //Blog: http://www.cnblogs.com/fraud/ 4 //##################### 5 #include <iostream> 6 #include <sstream> 7 #include <ios> 8 #include <iomanip> 9 #include <functional> 10 #include <algorithm> 11 #include <vector> 12 #include <string> 13 #include <list> 14 #include <queue> 15 #include <deque> 16 #include <stack> 17 #include <set> 18 #include <map> 19 #include <cstdio> 20 #include <cstdlib> 21 #include <cmath> 22 #include <cstring> 23 #include <climits> 24 #include <cctype> 25 using namespace std; 26 #define XINF INT_MAX 27 #define INF 0x3FFFFFFF 28 #define MP(X,Y) make_pair(X,Y) 29 #define PB(X) push_back(X) 30 #define REP(X,N) for(int X=0;X<N;X++) 31 #define REP2(X,L,R) for(int X=L;X<=R;X++) 32 #define DEP(X,R,L) for(int X=R;X>=L;X--) 33 #define CLR(A,X) memset(A,X,sizeof(A)) 34 #define IT iterator 35 typedef long long ll; 36 typedef pair<int,int> PII; 37 typedef vector<PII> VII; 38 typedef vector<int> VI; 39 struct edge{ 40 int to,cap,rev; 41 edge(int _to,int _cap,int _rev) 42 { 43 to=_to; 44 cap=_cap; 45 rev=_rev; 46 } 47 }; 48 const int MAX_V=10020; 49 vector<edge>G[MAX_V]; 50 int iter[MAX_V]; 51 int level[MAX_V]; 52 int tot=0; 53 void add_edge(int from,int to,int cap) 54 { 55 G[from].PB(edge(to,cap,G[to].size())); 56 G[to].PB(edge(from,0,G[from].size()-1)); 57 } 58 void bfs(int s,int t) 59 { 60 CLR(level,-1); 61 queue<int>q; 62 level[s]=0; 63 q.push(s); 64 while(!q.empty()) 65 { 66 int u=q.front(); 67 q.pop(); 68 for(int i=0;i<G[u].size();i++) 69 { 70 edge &e=G[u][i]; 71 if(e.cap>0&&level[e.to]<0) 72 { 73 level[e.to]=level[u]+1; 74 q.push(e.to); 75 } 76 } 77 } 78 } 79 int dfs(int v,int t,int f) 80 { 81 if(v==t)return f; 82 for(int &i=iter[v];i<G[v].size();i++) 83 { 84 edge &e=G[v][i]; 85 if(e.cap>0&&level[v]<level[e.to]) 86 { 87 int d=dfs(e.to,t,min(f,e.cap)); 88 if(d>0) 89 { 90 e.cap-=d;; 91 G[e.to][e.rev].cap+=d; 92 return d; 93 } 94 } 95 } 96 return 0; 97 } 98 int Dinic(int s,int t) 99 { 100 int flow=0; 101 for(;;) 102 { 103 bfs(s,t); 104 if(level[t]<0)return flow; 105 memset(iter,0,sizeof(iter)); 106 int f; 107 while((f=dfs(s,t,INF))>0) 108 { 109 flow+=f; 110 } 111 } 112 } 113 114 int a[MAX_V]; 115 int dp[MAX_V]; 116 int main() 117 { 118 ios::sync_with_stdio(false); 119 int n; 120 while(scanf("%d",&n)!=EOF){ 121 for(int i=0;i<n;i++) 122 scanf("%d",&a[i]); 123 int ans=0; 124 CLR(dp,0); 125 for(int i=0;i<n;i++){ 126 dp[i]=1; 127 for(int j=0;j<i;j++){ 128 if(a[j]<a[i]){ 129 dp[i]=max(dp[i],dp[j]+1); 130 } 131 } 132 ans=max(ans,dp[i]); 133 } 134 int s=2*n,t=2*n+1; 135 for(int i=0;i<t+1;i++)G[i].clear(); 136 for(int i=0;i<n;i++)add_edge(i,i+n,1); 137 for(int i=0;i<n;i++){ 138 if(dp[i]==1)add_edge(s,i,1); 139 if(dp[i]==ans)add_edge(i+n,t,1); 140 for(int j=i+1;j<n;j++){ 141 if(dp[j]==dp[i]+1&&a[i]<a[j]){ 142 add_edge(i+n,j,1); 143 } 144 } 145 } 146 printf("%d\n",ans); 147 printf("%d\n",Dinic(s,t)); 148 149 } 150 return 0; 151 }