Topic: Given an no-show graph, the number of schemes to find the minimum spanning tree
First of all, for a graph of the smallest spanning tree, the number of edges of each edge right is certain
First of all, let's run through the Kruskal, find out the number of occurrences of each edge right on the smallest spanning tree
Then for each of the Benquan that appear on the smallest spanning tree, we start from small to large
For each edge, we enumerate how many of these edge-weighted edges can be added to the minimum spanning tree without forming a ring.
Ans takes this value and then indents all the Unicom blocks that are connected by this edge right.
Note Output 0 when the minimum spanning tree does not exist
#include <map> #include <cstdio> #include <cstring> #include <iostream> #include <algorithm > #define M 1010#define Mo 31011using namespace std;struct edge{int X,y,f;bool operator < (const edge &Z) const{r Eturn f < z.f;}} Edges[m];int n,m,ans=1,fa[110];int digit[m+100];map<int,int>a;int Find (int x) {if (!fa[x]| | FA[X]==X) return Fa[x]=x;return fa[x]=find (fa[x]);} void Kruskal () {int i,cnt=0;memset (fa,0,sizeof FA); for (i=1;i<=m;i++) {int X=find (edges[i].x), Y=find (EDGES[I].Y); if (x==y) continue;fa[x]=y;cnt++;a[edges[i].f]++;} if (cnt!=n-1) {puts ("0"); exit (0);}} int Deal (int x) {int i,j,y,re=0,cnt=a[edges[x].f];for (y=x;edges[y].f==edges[y+1].f;y++); for (i=0;i<1<<y-x+ 1;i++) if (digit[i]==cnt) {int temp=i;memset (fa,0,sizeof FA); for (j=x;temp;temp>>=1,j++) if (temp&1) {int xx= Find (edges[j].x); int yy=find (EDGES[J].Y); if (Xx==yy) break;fa[xx]=yy;} if (!temp) ++re;} Ans*=re,ans%=mo;memset (fa,0,sizeof FA); for (i=x;i<=y;i++) {int Xx=find (edges[i].x), Yy=find (edges[i].y); if (Xx==yy) continue;fa[xx]=yy;} for (i=y+1;i<=m;i++) Edges[i].x=find (edges[i].x), Edges[i].y=find (EDGES[I].Y); return y;} int main () {int i;for (i=0;i<1<<10;i++) digit[i]=digit[i>>1]+ (i&1); Cin>>n>>m;for (I=1 ; i<=m;i++) scanf ("%d%d%d", &edges[i].x,&edges[i].y,&edges[i].f); sort (edges+1,edges+m+1); Kruskal (); for (i=1;i<=m;i++) if (A[edges[i].f]) i=deal (i); Cout<<ans<<endl;return 0;}
Bzoj 1016 JSOI2008 minimum spanning tree count Kruskal