n个点最少要n-1条边才能连通,可以删除一条边,最多删除2条边,然后枚举删除的1条边或2条边,用并查集判断是否连通,时间复杂度为O(n^3)
这边犯了个错误,
for(int i=0;i<N;i++){
fa[i]=i;
}
这个将i<=N,导致错误,值得注意
AC代码:
1 #pragma comment(linker, "/STACK:1024000000,1024000000") 2 #include<iostream> 3 #include<cstdio> 4 #include<cstring> 5 #include<cmath> 6 #include<math.h> 7 #include<algorithm> 8 #include<queue> 9 #include<set> 10 #include<bitset> 11 #include<map> 12 #include<vector> 13 #include<stdlib.h> 14 #include <stack> 15 using namespace std; 16 #define PI acos(-1.0) 17 #define max(a,b) (a) > (b) ? (a) : (b) 18 #define min(a,b) (a) < (b) ? (a) : (b) 19 #define ll long long 20 #define eps 1e-10 21 #define MOD 1000000007 22 #define N 106 23 #define inf 1e12 24 int n,fa[N],a[N],b[N]; 25 void init(){ 26 for(int i=0;i<N;i++){ 27 fa[i]=i; 28 } 29 } 30 int find(int x){ 31 return fa[x]==x?x:fa[x]=find(fa[x]); 32 } 33 int main() 34 { 35 int t; 36 scanf("%d",&t); 37 while(t--){ 38 scanf("%d",&n); 39 for(int i=0;i<=n;i++){ 40 scanf("%d%d",&a[i],&b[i]); 41 } 42 int ans=0; 43 for(int i=0;i<=n;i++){//删除一条边 44 init(); 45 int cnt=n; 46 for(int j=0;j<=n;j++){ 47 if(j!=i){ 48 int root1=find(a[j]); 49 int root2=find(b[j]); 50 if(root1!=root2){ 51 fa[root1]=root2; 52 cnt--; 53 } 54 } 55 } 56 if(cnt==1) ans++; 57 } 58 59 for(int i=0;i<=n;i++){//删除两条边 60 for(int j=i+1;j<=n;j++){ 61 init(); 62 int cnt=n; 63 for(int k=0;k<=n;k++){ 64 if(k!=i && k!=j){ 65 int root1=find(a[k]); 66 int root2=find(b[k]); 67 if(root1!=root2){ 68 fa[root1]=root2; 69 cnt--; 70 } 71 } 72 } 73 if(cnt==1)ans++; 74 } 75 } 76 printf("%d ",ans); 77 78 } 79 return 0; 80 }
贴上别人写bfs代码:
1 #include<cstdio> 2 #include<cstring> 3 int n,m; 4 struct note{ 5 int to,next; 6 }a[210]; 7 int head[105]; 8 bool used[105]; 9 bool des[210]; 10 int que[1005]; 11 bool bfs(){ 12 memset(used,false,sizeof(used)); 13 int start=0,aim=0; 14 que[aim++]=1; 15 used[1]=true; 16 while(start<aim){ 17 int num=que[start++]; 18 for(int i=head[num];i!=-1;i=a[i].next){ 19 if(!des[i])continue; 20 if(used[a[i].to])continue; 21 used[a[i].to]=true; 22 que[aim++]=a[i].to; 23 } 24 } 25 bool judge=true; 26 for(int i=1;i<=n;i++){ 27 if(!used[i])judge=false; 28 } 29 return judge; 30 } 31 int main(){ 32 int T; 33 // freopen("5631.txt","r",stdin); 34 scanf("%d",&T); 35 while(T--){ 36 scanf("%d",&n); 37 int coun=0; 38 memset(head,-1,sizeof(head)); 39 m=n; 40 for(int i=0;i<=m;i++){ 41 int x,y; 42 scanf("%d%d",&x,&y); 43 a[coun].to=y; 44 a[coun].next=head[x]; 45 head[x]=coun++; 46 a[coun].to=x; 47 a[coun].next=head[y]; 48 head[y]=coun++; 49 } 50 int ans=0; 51 memset(des,true,sizeof(des)); 52 for(int i=0;i<=m;i++){ 53 for(int j=i+1;j<=m;j++){ 54 des[i<<1]=des[i*2+1]=des[j*2]=des[j*2+1]=false; 55 if(bfs())ans++; 56 des[i<<1]=des[i*2+1]=des[j*2]=des[j*2+1]=true; 57 } 58 } 59 for(int i=0;i<=m;i++){ 60 des[i<<1]=des[i*2+1]=false; 61 if(bfs())ans++; 62 des[i<<1]=des[i*2+1]=true; 63 } 64 printf("%d ",ans); 65 } 66 return 0; 67 }