分析

假如实验皿是二维的,那么这道题便是一个二分图最小点覆盖问题,可以转化为二分图最大匹配问题,使用匈牙利算法解决。

考虑如何扩展到三维,首先我们发现一次操作的代价为\(min(x,y,z)\)。不难想到(\(?\)),每次操作的\(x,y,z\)中有一项为\(1\),另外两项为相应的最大值,即每次操作这个长方体的一个面(一“片”)时可以使答案最优。

题目中有一个限制条件为\(a \times b \times c \leq 5000\),可以发现\(min(a,b,c) \leq 17\)。假设\(c=min(a,b,c)\),我们可以把这个长方体分成\(c\)层,然后\(2^c\)枚举这\(c\)层中操作了哪些层。对于剩下的两维,便是第一段所述的二分图最小点覆盖问题。

代码

#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <cctype>
#include <algorithm>
#define rin(i,a,b) for(int i=(a);i<=(b);i++)
#define rec(i,a,b) for(int i=(a);i>=(b);i--)
#define trav(i,a) for(int i=head[(a)];i;i=e[i].nxt)
using std::cin;
using std::cout;
using std::endl;
typedef long long LL; inline int read(){
int x=0;char ch=getchar();
while(ch<'0'||ch>'9') ch=getchar();
while(ch>='0'&&ch<='9'){x=(x<<3)+(x<<1)+ch-'0';ch=getchar();}
return x;
} const int MAXN=5005;
int n,m,h,tot;
int xx[MAXN],yy[MAXN],zz[MAXN];
int head[MAXN],ecnt;
int match[MAXN],tag;
int vis[MAXN];
struct Edge{
int to,nxt;
}e[MAXN]; inline void add_edge(int bg,int ed){
ecnt++;
e[ecnt].to=ed;
e[ecnt].nxt=head[bg];
head[bg]=ecnt;
} int dfs(int x){
trav(i,x){
int ver=e[i].to;
if(vis[ver]==tag) continue;
vis[ver]=tag;
if(!match[ver]||dfs(match[ver])){
match[ver]=x;
return 1;
}
}
return 0;
} int main(){
int T=read();
while(T--){
int typ;
h=read(),n=read(),m=read();
if(h<=std::min(n,m)) typ=1;
else if(n<=std::min(h,m)) typ=2;
else typ=3;
tot=0;
rin(i,1,h) rin(j,1,n) rin(k,1,m){
int temp=read();
if(!temp) continue;
tot++;
if(typ==1) zz[tot]=i,xx[tot]=j,yy[tot]=k;
else if(typ==2) zz[tot]=j,xx[tot]=i,yy[tot]=j;
else zz[tot]=k,xx[tot]=i,yy[tot]=j;
}
int hh=h,nn=n,mm=m;
if(typ==2) h=nn,n=hh;
else if(typ==3) h=mm,n=hh,m=nn;
int S=(1<<h)-1,ans=1e9;
rin(i,0,S){
int temp=__builtin_popcount(i);
ecnt=0;
rin(j,1,n) head[j]=0;
rin(j,1,m) match[j]=0;
rin(j,1,tot){
if((i>>(zz[j]-1))&1) continue;
add_edge(xx[j],yy[j]);
}
rin(j,1,n){
tag++;
if(dfs(j)) temp++;
if(temp>=ans) break;
}
ans=std::min(ans,temp);
}
printf("%d\n",ans);
}
return 0;
}

[BZOJ3140][HNOI2013]消毒:二分图匹配的更多相关文章

  1. [BZOJ3140][HNOI2013]消毒(二分图最小点覆盖)

    3140: [Hnoi2013]消毒 Time Limit: 10 Sec  Memory Limit: 128 MBSubmit: 1621  Solved: 676[Submit][Status] ...

  2. BZOJ.3140.[HNOI2013]消毒(二分图匹配 匈牙利)

    题目链接 不难想到每次一定是切一片. 如果是平面,很容易想到直接做二分图匹配.对于3维的? 可以发现min(a,b,c)的最大值只有\(\sqrt[3]{n}≈17\),我们暴力枚举这一最小值代表的是 ...

  3. [HNOI2013] 消毒 - 二分图匹配

    容易发现 \(a,b,c\) 中至少有一个 \(\leq 17\) 不妨将其调剂为 \(a\),那么我们可以暴力枚举哪些 \(x\) 片片要被直接削掉,剩下的拍扁成二维情况 二维时,如果有一个格子是 ...

  4. bzoj3140: [Hnoi2013]消毒

    Description 最近在生物实验室工作的小T遇到了大麻烦. 由于实验室最近升级的缘故,他的分格实验皿是一个长方体,其尺寸为a*b*c,a.b.c 均为正整数.为了实验的方便,它被划分为a*b*c ...

  5. bzoj3140: [Hnoi2013]消毒(二分图)

    题目描述 最近在生物实验室工作的小T遇到了大麻烦. 由于实验室最近升级的缘故,他的分格实验皿是一个长方体,其尺寸为a*b*c,a.b.c 均为正整数.为了实验的方便,它被划分为a*b*c个单位立方体区 ...

  6. [luogu3231 HNOI2013] 消毒 (二分图最小点覆盖)

    传送门 Description 最近在生物实验室工作的小T遇到了大麻烦. 由于实验室最近升级的缘故,他的分格实验皿是一个长方体,其尺寸为abc,a.b.c 均为正整数.为了实验的方便,它被划分为abc ...

  7. bzoj千题计划295:bzoj3140: [Hnoi2013]消毒

    http://www.lydsy.com/JudgeOnline/problem.php?id=3140 如果只有两维,那就是二分图最小点覆盖 现在是三维,但是a*b*c<=5000,说明最小的 ...

  8. 【BZOJ3140】消毒(二分图匹配)

    [BZOJ3140]消毒(二分图匹配) 题面 Description 最近在生物实验室工作的小T遇到了大麻烦. 由于实验室最近升级的缘故,他的分格实验皿是一个长方体,其尺寸为abc,a.b.c 均为正 ...

  9. P3231 [HNOI2013]消毒

    P3231 [HNOI2013]消毒 二维覆盖我们已经很熟悉了 扩展到三维,枚举其中较小的一维,这里定义为$a$ 以$a$为关键字状压,$1$表示该面全选 剩下的面和二维覆盖一样二分图匹配 如果还没接 ...

随机推荐

  1. linux 正则表达式 目录

    linux 通配符与正则表达式 linux 通配符 linux 正则表达式 使用grep命令 linux 扩展正则表达式 egrep linux 正则表达式 元字符

  2. 数据库系统原理之SQL(四)

    数据库系统原理之SQL(四) 1. 数据更新 插入数据 INSERT-VALUES语句 #插入多条数据 insert [into] table_name (column_name,...) value ...

  3. JGit、SvnKit - 版本提交日志(1)提取

    1.相关开源jar包  1>使用JGIT访问git项目  2>使用SVNkit访问svn Git官方JGit使用教程指导 2.Git历史提交日志导出到文件 在项目根目录执行如下命令,将日志 ...

  4. 极*Java速成教程 - (8)

    Java高级特性 注解 注解可以在代码之外添加更多的信息,更加完整地描述程序,帮助编译器进行工作,或者实现某些特定的Java代码之外的功能. 注解可以简化某些重复的流程,自动化那些过程. 注解的使用 ...

  5. 《剑指offer》面试题26 复杂链表的复制 Java版

    (定义一个新的数据结构,每个节点除了具有普通链表的next域外,还有一个额外的引用指向任意节点.我们要对由该特殊数据结构形成的链表进行复制.) 我的方法:也就是克隆一个这种特殊链表,很快想到先不考虑原 ...

  6. c++多线程并发学习笔记(0)

    多进程并发:将应用程序分为多个独立的进程,它们在同一时刻运行.如图所示,独立的进程可以通过进程间常规的通信渠道传递讯息(信号.套接字..文件.管道等等). 优点:1.操作系统在进程间提供附附加的保护操 ...

  7. 一张图说明移动前端开发与web前端开发的区别

  8. C#多线程下更新UI的几种方法

    1. 使用UI线程的SynchronizationContext的Post/Send方法,这种情况一般在窗体构造函数或者FormLoad中获取同步上下文: 范例: public partial cla ...

  9. switch语句能否作用在byte,long,string上

    switch是java中的多分支结构.在switch(expr)中,expr只能是一个整数表达式,或者是枚举常量,整数表达式可以是int基本类型也可以是Integer包装类型,由于byte,short ...

  10. IDEA闪退问题

    这段时间经常遇到IDEA闪退的问题,在网上搜了一大堆的博客,无外乎是说让修改下面两个文件,但是改来改去没什么卵用,最后重装IDEA,一样的,没什么用.持续时间有几个月了,内心也有点崩溃,昨天下午彻底心 ...