題目描述
假設乙個試題庫中有n道試題。每道試題都標明了所屬類別。同一道題可能有多個類別屬性。現要從題庫中抽取m 道題組成試卷。並要求試卷包含指定型別的試題。試設計乙個滿足要求的組卷演算法。
對於給定的組卷要求,計算滿足要求的組卷方案。
輸入格式
第1行有2個正整數k和n (2 <=k<= 20, k<=n<= 1000)
k 表示題庫中試題型別總數,n 表示題庫中試題總數。第2 行有k 個正整數,第i 個正整數表示要選出的型別i的題數。這k個數相加就是要選出的總題數m。接下來的n行給出了題庫中每個試題的型別資訊。每行的第1 個正整數p表明該題可以屬於p類,接著的p個數是該題所屬的型別號。
輸出格式
第i 行輸出 「i:」後接型別i的題號。如果有多個滿足要求的方案,只要輸出1個方案。如果問題無解,則輸出「no solution!」。
輸入輸出樣例
輸入
3 15
3 3 4
2 1 2
1 31 3
1 31 3
3 1 2 3
2 2 3
2 1 3
1 21 2
2 1 2
2 1 3
2 1 2
1 13 1 2 3
輸出
1: 1 6 8
2: 7 9 10
3: 2 3 4 5
這道題就是乙個簡單的最大流,一般看到這道題,我們不難想到用網路流,然後考慮建圖:
因為我們要保證每道題只用一次,所以我們超級源點s到每道題的流量為 1 即可,題到知識點的流量也為 1 ,每個知識點到超級匯點t的流量為題目要求的就行,最後判斷最大流是否等於m即可。
考慮輸出解:(方法挺多的)
對於每一道題,我們判斷題到知識點的流量是否已經被流完了,就可以判斷出是否用過這道題,而且可以判斷出在哪乙個知識點用的這道題,最後我們把答案存起來,最後按照每道題輸出即可。
其實寫匈牙利更簡單。。。。
ac**:
#pragma gcc optimize(2)
#include
#define int long long
using namespace std;
const
int n=
2000010
,m=2010
;const
int inf=
0x3f3f3f3f
;int k,n,m,s,t,h[m]
;int head[m]
,nex[n]
,w[n]
,to[n]
,tot=1;
vector<
int> res[m]
;inline
void
ade(
int a,
int b,
int c)
inline
void
add(
int a,
int b,
int c)
intbfs()
}}return h[t];}
intdfs
(int x,
int f)}if
(!fl) h[x]=-
1;return fl;
}int
dinic()
signed
main()
for(
int i=
1;i<=n;i++)}
if(dinic()
!=m)
return
puts
("no solution!"),
0;for(
int i=
1;i<=n;i++)}
for(
int i=
1;i<=k;i++
)return0;
}
試題庫問題
假設乙個試題庫中有n道試題。每道試題都標明了所屬類別。同一道題可能有多個類別屬性。現要從題庫中抽取 m 道題組成試卷。並要求試卷包含 指定型別的試題。試設計乙個滿足要求的組卷演算法。對於給定的組卷要求,計算滿足要求的組卷方案。由檔案input.txt提供輸入資料。檔案第1行有2個正整數n和k 2 k...
試題庫問題
網路流24題裡面的,這題應該不算難,建圖比較簡單,就是把源點和型別連一條流量為需求題的邊,把型別和對應的題連一條流量為1的邊,把題和匯點連一條流量為1 的邊,保證每道題只用一次。然後找型別和題之間滿流的邊,表示這題在裡面。include include include include using n...
試題庫問題
匈牙利演算法 這是題目 因為是網路流24題網路流十分擅長這種求關係的題目,所以我們優先考慮寫網路流。對於網路流一類的問題,我們優先開啟畫圖軟體思考如何建模。首先我們先把這些題目與型別之間建一條邊 接著再把這些無向邊變成有向邊,然後再加上源節點s與匯節點t,再把源節點與型別相連,把題目與匯節點相連 這...