ZOJ 2601 Warehouse Keeper (fee flow)

Source: Internet
Author: User
Tags cos integer numbers

ZOJ 2601 Warehouse Keeper

The company where Jerry works owns a number of warehouses so can be used to store various goods. For each warehouse the types of goods the can is stored in this warehouse is known. To avoid problems with taxes, each warehouse must store is only one type of goods, and each type of goods must is stored in a T most one warehouse.

Jerry is planning to receive a new lot of goods in a couple of days and he must store the goods in the warehouses. However there is some goods in some warehouses already and Jerry wants to move as few of them as possible.

Help him to find the maximal number of types of goods so he can store in the warehouses and the minimal number of goods He must move in order to do.

Input

The input contains multiple test cases. The first line of the input was a single integer t (1 <= t <= Max) which is the number of the test cases. T test Cases Follow, each preceded to a single blank line.

The first line of all test case contains integer numbers m and N (2 <= m, n <=)-the number of warehouses and The number of types of goods respectively.

The following m lines describe warehouses. Each line contains ki-the number of various types of goods the can is stored in this warehouse (remember, only one type of goods can is stored in a warehouse at a time), followed by Ki integer numbers-the types of goods the can be stored.

The last line contains M integer numbers-for all warehouse either 0 is provided if there are no goods in this warehouse, or the type of goods is currently stored in this warehouse if there is one. It is guaranteed the initial configuration is correct, which is, each warehouse stores the goods it can store, and no The type of goods is stored in and more than one warehouse.

Output

For each case, on the first line print p-the maximal number of types of goods so can be stored in the warehouses, and Q-the minimal number of goods that need to being moved in order to do. After that output m integer numbers-for each warehouse output the type of goods that must is stored in this warehouse, O R 0 if none must be.

Remember that's the only move goods that is already stored in some houses to other ones, and you aren't allowed to dispose them.

The consecutive cases should is separated by a and blank line. No blank line should is produced after the last Test case.

Sample Input

2

4 5
3 1 2 3
2 1 2
2 1 2
3 1 4 5
0 2 0 1

2 2
1 1
1 2
0 0

Sample Output

4 1
3 2 1 4

2 0
1 2

The main topic: There are n warehouses, m kinds of goods, each warehouse can only store a few specified goods. Whenever a warehouse is stocked with one kind of goods, it is no longer possible to store other kinds of goods. Now, some warehouses have already deposited the goods, ask how to keep the N warehouses as many kinds of goods as possible, under the premise of minimizing the amount of goods already in the mobile warehouse. Solution idea: Set a super source point, connect to all the warehouses, the capacity is 1, the cost is 0. Set up a super meeting point so that all cargo types are connected to the Super meeting point, with a capacity of 1 and a cost of 0. Then, the warehouse, to all of the goods he can store, the capacity is 1, but the cost is different, if the goods are stored in the warehouse of the type of goods, then the cost of 0, if not the cost of 1, so run the cost of the flow, you can prioritize the use of existing warehouses of goods, to avoid unnecessary exchange.
#include <cstdio>#include <cstring>#include <algorithm>#include <cmath>#include <cstdlib>#include <vector>#include <queue>using namespace STD;typedef Long LongllConst intN = -;Const intM =50000;Constll INF =1e18; vector<int>Wk[n];intN, M, S, t;intRec[n];intPre[n], inq[n]; ll A[n], d[n];structedge{intFrom, to;    ll cap, flow; llCos;}; vector<Edge>Edges vector<int>G[M];voidInit () {memset(REC,0,sizeof(rec)); for(inti =0; I <= N; i++) wk[i].clear (); for(inti =0; I <= n + M + n * m;    i++) g[i].clear (); Edges.clear ();}voidAddedge (intFromintTo, LL cap, LLCos{Edges.push_back (Edge) {from, to, Cap,0,Cos}); Edges.push_back (Edge) {To, from,0,0, -Cos});intm = Edges.size (); G[from].push_back (M-2); G[to].push_back (M-1);}intBF (intSintT, ll& Flow, ll& cost) { Queue<int>Q;memset(INQ,0,sizeof(INQ));memsetA0,sizeof(a));memset(Pre,0,sizeof(pre)); for(inti =0; i < N;    i++) D[i] = INF; D[s] =0;    A[s] = INF; Inq[s] =1; Pre[s] =0; Q.push (s); while(! Q.empty ()) {intU = Q.front ();        Q.pop (); Inq[u] =0; for(inti =0; I < g[u].size (); i++) {Edge &e = edges[g[u][i]];if(E.cap > E.flow && d[e.to] > D[u] + E.Cos) {d[e.to] = D[u] + E.Cos;                A[e.to] = min (A[u], e.cap-e.flow); Pre[e.to] = G[u][i];if(!inq[e.to]) {Inq[e.to] =1;                Q.push (e.to); }            }           }    }if(D[t] = = INF)return 0;    Flow + = A[t]; Cost + = (LL) d[t] * (LL) a[t]; for(intu = t; U! = S;        U = edges[pre[u]].from) {Edges[pre[u]].flow + = a[t]; edges[pre[u]^1].flow-= a[t]; }return 1;}intMCMF (intSintT, ll& cost) {ll flow =0; Cost =0; while(BF (S, t, flow, cost));returnFlow;}voidInput () {s =0, t = n + M +3;intA, B; for(inti =1; I <= N; i++) {scanf("%d", &a); for(intj =0; J < A; J + +) {scanf("%d", &b);        Wk[i].push_back (b); }    } for(inti =1; I <= N; i++) {scanf("%d", &rec[i]); }}voidBuild () { for(inti =1; I <= N; i++) Addedge (s, I,1,0); for(inti =1; I <= m; i++) Addedge (i + N, T,1,0); for(inti =1; I <= N; i++) { for(intj =0; J < Wk[i].size (); J + +) {if(Wk[i][j] = = Rec[i]) Addedge (i, rec[i] + N,1,0);ElseAddedge (i, wk[i][j] + N,1,1); }       }}voidPrint () {intAns[n]; ll cost;inttemp = MCMF (s, t, cost);printf("%d", temp);intFlag2; for(inti =1; I <= N; i++) {Flag2 =0; for(intj =0; J < G[i].size (); J + +) {if(Edges[g[i][j]].flow >0) {Flag2 =1;            Ans[i] = edges[g[i][j]].to-n; }        }if(!FLAG2) {Ans[i] =0; }    }intCNT =0; for(inti =1; I <= N; i++) {if(!rec[i])Continue;if(Rec[i]! = ans[i]) cnt++; }printf("%d\n", CNT);printf("%d", ans[1]); for(inti =2; I <= N; i++) {printf("%d", Ans[i]); }puts("");}intMain () {intTscanf("%d", &t); while(t--) {scanf("%d%d", &n, &m);        Init ();        Input ();        Build (); Print ();ifTputs(""); }return 0;}

Copyright NOTICE: This article for Bo Master original article, without BO Master permission cannot reprint.

ZOJ 2601 Warehouse Keeper (fee flow)

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.