HK commonly known as algorithms. And a function Hungarian algorithm, but the complexity of the better. Hungarian algorithm complexity O (VE), HK algorithm complexity O (sqrt (V) * E).
But it is easy to write collapse, do not ask how I know.
. 1 #include <bits / STDC ++ H.> 2 the using namespace STD; . 3 const int MAXN = 500 ; // maximum number of points . 4 const int INF = . 1 << 28 ; // from the initial value . 5 int BMAP [MAXN] [MAXN] ; // bipartite FIG . 6 int CX [MAXN]; // CX [i] represents the set of left and right set of vertex number i matches the vertex . 7 int CY [MAXN]; // CY [i] represents the set of the right vertex i matching set of left vertex number . 8 int NX, NY; . 9 int DX [MAXN]; 10 int Dy [MAXN]; . 11 / * DX [i] represents the number i from the set of left vertex, dy [i] denotes the set of i vertices of a right distance number * / 12 is int DIS; 13 is BOOL bmask [MAXN]; 14 // Looking augmenting path set 15 BOOL SearchPath () 16 { . 17 Queue < int > Q; 18 is DIS = INF; . 19 Memset (DX, - . 1 , the sizeof (DX)); // the first layers 20 is Memset (Dy, - . 1 , the sizeof (Dy)); 21 is for ( int= i . 1 ; i <= NX; i ++ ) 22 is { 23 is // CX [i] represents the set of the right-left vertex number i matches the set of vertices 24 IF (CX [i] == - . 1 ) 25 { 26 is // the non-traversing node enqueue and initializes the secondary node distance is 0 27 Q.push (I); 28 DX [I] = 0 ; // 0 layer 29 } 30 } 31 // breadth first Search augmenting path 32 the while ( ! Q.empty ()) 33 is { 34 is int U = Q.front (); 35 Q.pop (); 36 IF (DX [U]> DIS) BREAK ; 37 [ // take the right node 38 is for ( int V = . 1 ; V <= NY; V ++ ) 39 { 40 // right node by wide path distance 41 is IF (BMAP [u] [V] && Dy [V] == - 1 ) 42 is { 43 is Dy [V] = DX [u] + 1 ; // V a distance corresponding to a distance which corresponds to u 44 is IF (CY [V] == - . 1 ) DIS = Dy [V]; // If the node is not matched, then the augmented channel forming 45 the else //If the match point, and then down and then search 46 is { 47 DX [CY [V]] = Dy [V] + . 1 ; 48 Q.push (CY [V]); 49 } 50 } 51 is } 52 is } 53 is return ! DIS = INF; 54 is } 55 // find the path search depth 56 is int FindPath ( int U) 57 is { 58 for ( int V = . 1 ; V <= NY; V ++ ) 59 { 60 //If the point has not been traversed and the distance of a node + 1'd 61 is IF (! Bmask [V] && BMAP [U] [V] && Dy [V] == DX [U] + . 1 ) 62 is { 63 is // the dyeing point 64 bmask [V] = . 1 ; 65 IF (! CY [V] = - . 1 && Dy [V] == DIS) // If the point has been matched and the matching point is the last, then this path is not augmenting paths. That road nodes already matched 66 { 67 Continue ; 68 } 69 IF (CY [V] == - . 1 || FindPath (CY [V])) // if the point does not match or later point can make room, then this is augmenting path 70 { 71 CY [V] = U; CX [U] = V; 72 return . 1 ; 73 is } 74 } 75 } 76 return 0 ; 77 } 78 // get the maximum number of matches 79 int MaxMatch () 80 { 81 int RES = 0 ; 82 Memset (CX, - . 1 , the sizeof (CX)); 83 Memset (CY, - . 1 , the sizeof (CY)); // CX [i] represents the set of i vertices of the right and left of the matched set of vertices No. 84 the while (SearchPath ()) // if there is an augmenting path up to iteration without augmenting path 85 { 86 Memset (bmask, 0 , the sizeof (bmask)); // tag array 87 for ( int I = . 1 ; I <= NX; I ++ ) 88 { 89 IF (CX [I] == - . 1 ) 90 { 91 is RES = + FindPath (I); 92 } 93 } 94 } 95 return RES; 96 } 97 int main() 98 { 99 int num; 100 scanf("%d",&num); 101 while(num--) 102 { 103 memset(bmap,0,sizeof(bmap)); 104 scanf("%d%d",&nx,&ny); 105 for(int i=1;i<=nx;i++) 106 { 107 int snum; 108 scanf("%d",&snum); 109 int u; 110 for(int j=1;j<=snum;j++) 111 { 112 scanf("%d",&u); 113 bmap[i][u]=1; 114 // bmap[u][i]=1; 115 } 116 } 117 // cout<<MaxMatch()<<endl; 118 if(MaxMatch()==nx) 119 { 120 printf("YES\n"); 121 } 122 else 123 { 124 printf("NO\n"); 125 } 126 } 127 //system("pause"); 128 return 0; 129 }