题解Luogu P2763 试题库问题

Posted yzhang-rp-inf

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了题解Luogu P2763 试题库问题相关的知识,希望对你有一定的参考价值。

原题传送门

这题很简单啊

从源点向k类题目分别连流量为所需数量的边

从每道题向汇点连一条流量为1的边(每题只能用1次)

从类型向对应的题目连一条流量为1的边

跑一边最大流

如果最大流小于所需题目数量,就无解

否则对于每个类型,看每道题是否要选

#include <bits/stdc++.h>
#define inf 0x3f3f3f3f 
#define M 80005
#define N 2005
//#define getchar nc
using namespace std;
inline char nc(){
    static char buf[100000],*p1=buf,*p2=buf;
    return p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++;
}
inline int read()
{
    register int x=0,f=1;register char ch=getchar();
    while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
    while(ch>='0'&&ch<='9')x=(x<<3)+(x<<1)+ch-'0',ch=getchar();
    return x*f;
}
inline void write(register int x)
{
    if(!x)putchar('0');if(x<0)x=-x,putchar('-');
    static int sta[20];register int tot=0;
    while(x)sta[tot++]=x%10,x/=10;
    while(tot)putchar(sta[--tot]+48);
}
inline int Min(register int a,register int b)
{
    return a<b?a:b;
}
struct node{
    int to,nxt,v;
}e[M];
int head[N],cnt=1;
inline void add(register int u,register int v,register int val)
{
    e[++cnt]=(node){v,head[u],val};
    head[u]=cnt;
}
int n,k,s,t,nn,maxflow=0,sum=0;
int dep[N],gap[N],cur[N];
inline void bfs()
{
    memset(dep,-1,sizeof(dep));
    memset(gap,0,sizeof(gap));
    dep[t]=0;
    ++gap[dep[t]];
    queue<int> q;
    q.push(t);
    while(!q.empty())
    {
        int u=q.front();
        q.pop();
        for(register int i=head[u];i;i=e[i].nxt)
        {
            int v=e[i].to;
            if(dep[v]!=-1)
                continue;
            q.push(v);
            dep[v]=dep[u]+1;
            ++gap[dep[v]];
        }
    }
}
inline int dfs(register int u,register int flow)
{
    if(u==t)
    {
        maxflow+=flow;
        return flow;
    }
    int used=0;
    for(register int i=cur[u];i;i=e[i].nxt)
    {
        cur[u]=i;
        int v=e[i].to;
        if(e[i].v&&dep[v]+1==dep[u])
        {
            int tmp=dfs(v,Min(e[i].v,flow-used));
            if(tmp)
            {
                e[i].v-=tmp;
                e[i^1].v+=tmp;
                used+=tmp;
            }
            if(used==flow)
                return used;
        }
    }
    --gap[dep[u]++]==0?dep[s]=nn+1:++gap[dep[u]];
    return used;
}
inline void ISAP()
{
    bfs();
    while(dep[s]<nn)
    {
        memcpy(cur,head,sizeof(head));
        dfs(s,inf);
    }
}
int main()
{
    k=read(),n=read();
    s=0,t=k+n+1;
    for(register int i=1;i<=k;++i)
    {
        int x=read();
        add(s,i,x),add(i,s,0),sum+=x;
    }
    for(register int i=1;i<=n;++i)
    {
        int p=read();
        for(register int j=1;j<=p;++j)
        {
            int x=read();
            add(x,i+k,1),add(i+k,x,0);  
        }
        add(i+k,t,1),add(t,i+k,0);
    }
    nn=n+k+2;
    ISAP();
    if(maxflow==sum)
        for(register int u=1;u<=k;++u)
        {
            write(u),putchar(':'),putchar(' ');
            for(register int i=head[u];i;i=e[i].nxt)
                if(e[i].to!=0&&e[i].v==0)
                    write(e[i].to-k),putchar(' ');
            puts("");
        }
    else
        puts("No Solution!"); 
    return 0;
}

以上是关于题解Luogu P2763 试题库问题的主要内容,如果未能解决你的问题,请参考以下文章

洛谷P2763 试题库问题

洛谷 [P2763]试题库问题

P2763 试题库问题

P2763 试题库问题

洛谷 P2763 试题库问题最大流

CSP-J2022试题题解