网络流/最大流/二分or贪心
题目大意:有n个队伍,两两之间有一场比赛,胜者得分+1,负者得分+0,问最多有几只队伍打败了所有得分比他高的队伍?
可以想到如果存在这样的“strong king”那么一定是胜场较多的队伍……(比他赢得多的队伍num少,而他总共赢得场数times足够多,至少得满足times>=num吧?)
那么我们可以二分/枚举k,表示胜场前k多的队伍是stong king。(这题范围小,只有10支队伍,如果队伍较多我们就需要二分了……)
最最丧心病狂的是!!!出题人TMD卡读入!!!居然在数字与数字之间会有多个空格!!!像我这样直接遇到空格就a[++n]=v,v=0;的就挂了!!!
妈蛋害我调了一晚上!
1 Source Code 2 Problem: 2699 User: sdfzyhy 3 Memory: 716K Time: 0MS 4 Language: G++ Result: Accepted 5 6 Source Code 7 8 //POJ 2699 9 #include<vector> 10 #include<cstdio> 11 #include<sstream> 12 #include<cstring> 13 #include<cstdlib> 14 #include<iostream> 15 #include<algorithm> 16 #define rep(i,n) for(int i=0;i<n;++i) 17 #define F(i,j,n) for(int i=j;i<=n;++i) 18 #define D(i,j,n) for(int i=j;i>=n;--i) 19 #define pb push_back 20 using namespace std; 21 inline int getint(){ 22 int v=0,sign=1; char ch=getchar(); 23 while(ch<'0'||ch>'9'){ if (ch=='-') sign=-1; ch=getchar();} 24 while(ch>='0'&&ch<='9'){ v=v*10+ch-'0'; ch=getchar();} 25 return v*sign; 26 } 27 const int N=100,M=1000,INF=~0u>>2; 28 typedef long long LL; 29 /******************tamplate*********************/ 30 int n,m,tot,ans,num,a[N]; 31 char s1[N]; 32 struct edge{int to,v;}; 33 struct Net{ 34 edge E[M]; 35 int head[N],next[M],cnt; 36 void ins(int x,int y,int v){ 37 E[++cnt]=(edge){y,v}; 38 next[cnt]=head[x]; head[x]=cnt; 39 } 40 void add(int x,int y,int v){ 41 ins(x,y,v); ins(y,x,0); 42 } 43 int s,t,d[N],Q[M]; 44 bool mklevel(){ 45 F(i,0,t) d[i]=-1; 46 d[s]=0; 47 int l=0,r=-1; 48 Q[++r]=s; 49 while(l<=r){ 50 int x=Q[l++]; 51 for(int i=head[x];i;i=next[i]) 52 if (d[E[i].to]==-1 && E[i].v){ 53 d[E[i].to]=d[x]+1; 54 Q[++r]=E[i].to; 55 } 56 } 57 return d[t]!=-1; 58 } 59 int dfs(int x,int a){ 60 if (x==t) return a; 61 int flow=0; 62 for(int i=head[x];i && flow<a;i=next[i]) 63 if (E[i].v && d[E[i].to]==d[x]+1){ 64 int f=dfs(E[i].to,min(a-flow,E[i].v)); 65 E[i].v-=f; 66 E[i^1].v+=f; 67 flow+=f; 68 } 69 if (!flow) d[x]=-1; 70 return flow; 71 } 72 void Dinic(){ 73 while(mklevel()) ans+=dfs(s,INF); 74 } 75 void init(){ 76 n=0; 77 gets(s1); 78 int v=0; 79 stringstream ss(s1); 80 while(ss >> v) a[++n]=v; 81 } 82 bool check(int k){ 83 cnt=1; F(i,s,t) head[i]=0; 84 F(i,1,n) add(s,i,a[i]); 85 int l=n; 86 F(i,1,n) F(j,i+1,n){ 87 add(++l,t,1); 88 if(i>=k && a[j]>a[i]) add(i,l,1); 89 else add(i,l,1),add(j,l,1); 90 } 91 ans=0; 92 Dinic(); 93 return ans==m; 94 } 95 void solve(){ 96 m=n*(n-1)/2; 97 s=0; t=n+m+1; 98 int l=0,r=n,mid,as=0; 99 /* 100 while(l<=r){ 101 mid=l+r>>1; 102 // printf("l=%d r=%d mid=%d ",l,r,mid); 103 if (check(mid)) as=mid,r=mid-1; 104 else l=mid+1; 105 } 106 二分 */ 107 // D(i,n,1) if(!check(i)){as=i;break;} 108 109 F(i,1,n) if(check(i)){as=i-1;break;} 110 printf("%d ",n-as); 111 } 112 }G1; 113 114 int main(){ 115 #ifndef ONLINE_JUDGE 116 freopen("2699.in","r",stdin); 117 freopen("2699.out","w",stdout); 118 #endif 119 int T=getint(); 120 while(T--){ 121 G1.init();G1.solve(); 122 } 123 return 0; 124 }