2018QBXT刷題遊記(6)
阿新 • • 發佈:2018-11-07
【2018QBXT刷題遊記】
Day1 TEST2
T3 network
在電腦科學中,經常要通過分析變數之間的相關性來簡化計算過程。變數
間的相關性可以用有向圖
來表示,圖中的點表示變數,邊表示變數間
的關係。這裡
滿足:
中的所有邊都從編號小的點指向編號大的點。
從圖中選出一個點集
,如果
中的任意兩個點之間都有邊(方向是編
號小的點指向編號大的點),則稱
為團。特別地,空集也認為是一個團。
如果存在一個點,與
中的任意一個點之間都有邊( 方向是編號小的點指
向編號大的點),那麼稱 T 為可擴團。
如果一個團
不是可擴團,那麼稱它為極大團。
給出
,求
有多少個不同的極大團。
這裡
滿足一個性質:對於
中任意一個點
, 用
表示編號比 i 小的點
中所有與 i 有邊相連的點的集合,那麼
是一個團。
【分析】這題好水啊……orz
根據提供的性質,只需要按照從大到小的順序判斷每一個點i
若與它相連的最大點j的入度比當前點小
那麼以j為最大點的團一定是可擴團,i就是可擴點(還可能有更多)
注意重邊的判斷。
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
char c;int n,m,cnt,ans;int read(){c=getchar();int f=1,s=0;
while(c<'0'||c>'9')if(c=='-')f=-1,c=getchar();
while(c>='0'&&c<='9')s=s*10+c-'0',c=getchar();return f*s;}
struct Edge{
int a,b;
}E[1000007];
int tot[1000007],last[1000007];bool qwq[1000007];
bool cmp(Edge x,Edge y){
if(x.a!=y.a)return (x.a<y.a);
else return (x.b<y.b);
}
int main(){
freopen("network.in","r",stdin);
freopen("network.out","w",stdout);
n=read();m=read();
for(int i=1;i<=m;i++){
E[i].a=read();E[i].b=read();
}cnt=0;
sort(E+1,E+1+m,cmp);
for(int i=1;i<=m;i++){
cnt++;
E[cnt]=E[i];
while(i<m && E[i].a==E[i+1].a &&E[i].b==E[i+1].b)i++;
}m=cnt;
for(int i=1;i<=m;i++){
tot[E[i].b]++;
last[E[i].b]=max(E[i].a,last[E[i].b]);
}ans=0;
for(int i=n;i>=1;i--){
if(last[i] && tot[i]>tot[last[i]])qwq[last[i]]=1;
if(!qwq[i])ans++;
}
printf("%d\n",ans);
return 0;
}