期末考试终于完了,老班决定召开班委会,内容嘛,则是可爱的奖学金的问题((*^__^*)),她叫来了一些班委,每位班委提出了自己的意见:“我认为同学a的奖学金应该比b多!”老班决定要找出一种奖学金方案,满足各位班委的意见,且同时使得总奖学金数最少。每位同学奖学金最少为100元且都为整数。

 

INPUT:

第一行两个整数n,m,表示同学总数和班委意见数;
以下m行,每行2个整数a,b,表示某个班委认为第a号同学奖学金应该比第b号同学高。

2 1

1 2

 1 int dfs(int s)
 2 {
 3     vis[s]=1;
 4     if(!flag)
 5         return 0;
 6     for(int i=linkk[s];i;i=e[i].y)
 7     {
 8         if(vis[e[i].x])
 9         {
10             flag=0;
11             return 0;
12         }
13         else
14             dfs(e[i].x);
15     }
16     vis[s]=0;
17 }

 

CPP:

  1 #include<iostream>
  2 #include<string>
  3 #include<algorithm>
  4 #include<cstring>
  5 #include<cstdio>
  6 #include<cmath>
  7 #include<iomanip>
  8 #include<queue>
  9 #include<vector>
 10 #include<cstring>
 11 using namespace std;
 12 const int maxn=500001;
 13 int n,m;
 14 int linkk[maxn],len=0;
 15 int id[maxn],dis[maxn],vis[maxn];
 16 int ans=-1;
 17 int q[maxn];
 18 bool flag=1;
 19 struct node
 20 {
 21     int x,y,v;
 22 }e[maxn];
 23 
 24 void init(int xx,int yy)
 25 {
 26     e[++len].y=linkk[xx];linkk[xx]=len;
 27     e[len].x=yy;e[len].v=1;
 28     id[yy]++;
 29 }
 30 
 31 void SPFA()
 32 {
 33     int head=0,tail=0;
 34     int maxx=0;
 35     for(int i=1;i<=n;i++)
 36         if(id[i]==0)
 37             q[++tail]=i;
 38     while(head<=tail)
 39     {
 40         int tn=q[++head];
 41         int te=linkk[tn];
 42         for(int i=te;i;i=e[i].y)
 43         {
 44             int tmp=e[i].x;
 45             id[tmp]--;
 46             if(id[tmp]<0)
 47             {
 48                 ans=-1;
 49                 cout<<"impossible"<<endl;
 50                 exit(0);
 51             }
 52             dis[tmp]=max(dis[tmp],dis[tn]+e[i].v);
 53             ans=max(ans,dis[tmp]);
 54             if(id[tmp]==0)
 55                 q[++tail]=tmp;
 56         }
 57     }
 58 }
 59 
 60 int dfs(int s)
 61 {
 62     vis[s]=1;
 63     if(!flag)
 64         return 0;
 65     for(int i=linkk[s];i;i=e[i].y)
 66     {
 67         if(vis[e[i].x])
 68         {
 69             flag=0;
 70             return 0;
 71         }
 72         else
 73             dfs(e[i].x);
 74     }
 75     vis[s]=0;
 76 }
 77 
 78 int main()
 79 {
 80     /*freopen("2.in","r",stdin);
 81     freopen("2.out","w",stdout);*/
 82     //ios::sync_with_stdio(false);
 83     cin>>n>>m;
 84     for(int i=1;i<=m;i++)
 85     {
 86         int x,y;
 87         cin>>x>>y;
 88         init(y,x);
 89     }
 90     for(int i=1;i<=n;i++)
 91     {
 92         if(id[i]==0)
 93         {
 94             dfs(i);
 95             if(!flag)
 96             {
 97                 cout<<"impossible"<<endl;
 98                 return 0;
 99             }
100         }
101     }
102     SPFA();
103     if(ans!=-1)
104     {
105         ans=0;
106         for(int i=n;i>0;i--)
107         {
108             ans=ans+dis[i];
109             //cout<<dis[i]<<endl;
110         }            
111         ans=ans+n*100;
112         cout<<ans<<endl;
113     }
114     else
115         cout<<"impossible"<<endl;
116     return 0;
117 }
View Code

 

 

OUTPUT:

201

 

思路:

一道显然的查分约束题;不可能的条件为有环(但不一定是负环);

所以要在SPFA之前用DFS先判断一下是否有环。(卡了我两天)!

核心: