[ACM] POJ 3740 Easy Finding (DLX模板题)

2024-01-28 13:18
文章标签 模板 poj acm easy finding dlx 3740

本文主要是介绍[ACM] POJ 3740 Easy Finding (DLX模板题),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

Easy Finding
Time Limit: 1000MS Memory Limit: 65536K
Total Submissions: 16178 Accepted: 4343

Description

Given a M× N matrix A. A ij ∈ {0, 1} (0 ≤ i < M, 0 ≤ j < N), could you find some rows that let every cloumn contains and only contains one 1.

Input

There are multiple cases ended by EOF. Test case up to 500.The first line of input is M, N ( M ≤ 16, N ≤ 300). The next M lines every line contains N integers separated by space.

Output

For each test case, if you could find it output "Yes, I found it", otherwise output "It is impossible" per line.

Sample Input

3 3
0 1 0
0 0 1
1 0 0
4 4
0 0 0 1
1 0 0 0
1 1 0 1
0 1 0 0

Sample Output

Yes, I found it
It is impossible

Source

POJ Monthly Contest - 2009.08.23, MasterLuo

 

解题思路:

题意为由01组成的矩阵,问能不能挑出几行使组成的新矩阵每列只有一个1.

套用Dlx模板,不过G++ 超时,C++勉强能过。

代码:

#include <iostream>
#include <stdio.h>
using namespace std;
const int maxnode=5000;
const int maxm=310;
const int maxn=18;struct DLX
{int n,m,size;int U[maxnode],D[maxnode],R[maxnode],L[maxnode],Row[maxnode],Col[maxnode];int H[maxn];//行头节点int S[maxm];//每列有多少个节点int ansd,ans[maxn];//如果有答案,则选了ansd行,具体是哪几行放在ans[ ]数组里面,ans[0~ansd-1];void init(int _n,int _m){n=_n,m=_m;for(int i=0;i<=m;i++){S[i]=0;U[i]=D[i]=i;//初始状态下,上下自己指向自己L[i]=i-1;R[i]=i+1;}R[m]=0,L[0]=m;size=m;//编号,每列都有一个头节点,编号1-mfor(int i=1;i<=n;i++)H[i]=-1;//每一行的头节点}void link(int r,int c)//第r行,第c列{++S[Col[++size]=c];//第size个节点所在的列为c,当前列的节点数++Row[size]=r;//第size个节点行位置为rD[size]=D[c];//下面这四句头插法(图是倒着的?)U[D[c]]=size;U[size]=c;D[c]=size;if(H[r]<0)H[r]=L[size]=R[size]=size;else{R[size]=R[H[r]];L[R[H[r]]]=size;L[size]=H[r];R[H[r]]=size;}}void remove(int c)//删除节点c,以及c上下节点所在的行,每次调用这个函数,都是从列头节点开始向下删除,这里c也可以理解为第c列{                 //因为第c列的列头节点编号为cL[R[c]]=L[c];R[L[c]]=R[c];for(int i=D[c];i!=c;i=D[i])for(int j=R[i];j!=i;j=R[j]){U[D[j]]=U[j];D[U[j]]=D[j];--S[Col[j]];}}void resume(int c)//恢复节点c,以及c上下节点所在的行(同上,也可以理解为从第c列的头节点开始恢复{for(int i=U[c];i!=c;i=U[i])for(int j=L[i];j!=i;j=L[j])++S[Col[U[D[j]]=D[U[j]]=j]]; //打这一行太纠结了 T TL[R[c]]=R[L[c]]=c;}bool dance(int d)//递归深度{if(R[0]==0){ansd=d;return true;}int c=R[0];for(int i=R[0];i!=0;i=R[i])if(S[i]<S[c])c=i;remove(c);//找到节点数最少的列,当前元素不是原图上0,1的节点,而是列头节点for(int i=D[c];i!=c;i=D[i]){ans[d]=Row[i];//列头节点下面的一个节点for(int j=R[i];j!=i;j=R[j])remove(Col[j]);if(dance(d+1))//找到,返回return true;for(int j=L[i];j!=i;j=L[j])resume(Col[j]);}resume(c);return false;}
};DLX x;
int n,m;int main()
{while(scanf("%d%d",&n,&m)!=EOF){x.init(n,m);int num;for(int i=1;i<=n;i++){for(int j=1;j<=m;j++){cin>>num;if(num)x.link(i,j);}}if(!x.dance(0))printf("It is impossible\n");elseprintf("Yes, I found it\n");}return 0;
}


 

这篇关于[ACM] POJ 3740 Easy Finding (DLX模板题)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/653734

相关文章

利用Python打造一个Excel记账模板

《利用Python打造一个Excel记账模板》这篇文章主要为大家详细介绍了如何使用Python打造一个超实用的Excel记账模板,可以帮助大家高效管理财务,迈向财富自由之路,感兴趣的小伙伴快跟随小编一... 目录设置预算百分比超支标红预警记账模板功能介绍基础记账预算管理可视化分析摸鱼时间理财法碎片时间利用财

如何在 Spring Boot 中实现 FreeMarker 模板

《如何在SpringBoot中实现FreeMarker模板》FreeMarker是一种功能强大、轻量级的模板引擎,用于在Java应用中生成动态文本输出(如HTML、XML、邮件内容等),本文... 目录什么是 FreeMarker 模板?在 Spring Boot 中实现 FreeMarker 模板1. 环

IDEA自动生成注释模板的配置教程

《IDEA自动生成注释模板的配置教程》本文介绍了如何在IntelliJIDEA中配置类和方法的注释模板,包括自动生成项目名称、包名、日期和时间等内容,以及如何定制参数和返回值的注释格式,需要的朋友可以... 目录项目场景配置方法类注释模板定义类开头的注释步骤类注释效果方法注释模板定义方法开头的注释步骤方法注

C++中函数模板与类模板的简单使用及区别介绍

《C++中函数模板与类模板的简单使用及区别介绍》这篇文章介绍了C++中的模板机制,包括函数模板和类模板的概念、语法和实际应用,函数模板通过类型参数实现泛型操作,而类模板允许创建可处理多种数据类型的类,... 目录一、函数模板定义语法真实示例二、类模板三、关键区别四、注意事项 ‌在C++中,模板是实现泛型编程

SpringBoot集成图片验证码框架easy-captcha的详细过程

《SpringBoot集成图片验证码框架easy-captcha的详细过程》本文介绍了如何将Easy-Captcha框架集成到SpringBoot项目中,实现图片验证码功能,Easy-Captcha是... 目录SpringBoot集成图片验证码框架easy-captcha一、引言二、依赖三、代码1. Ea

SpringBoot整合easy-es的详细过程

《SpringBoot整合easy-es的详细过程》本文介绍了EasyES,一个基于Elasticsearch的ORM框架,旨在简化开发流程并提高效率,EasyES支持SpringBoot框架,并提供... 目录一、easy-es简介二、实现基于Spring Boot框架的应用程序代码1.添加相关依赖2.添

基于Java实现模板填充Word

《基于Java实现模板填充Word》这篇文章主要为大家详细介绍了如何用Java实现按产品经理提供的Word模板填充数据,并以word或pdf形式导出,有需要的小伙伴可以参考一下... Java实现按模板填充wor编程d本文讲解的需求是:我们需要把数据库中的某些数据按照 产品经理提供的 word模板,把数据

认识、理解、分类——acm之搜索

普通搜索方法有两种:1、广度优先搜索;2、深度优先搜索; 更多搜索方法: 3、双向广度优先搜索; 4、启发式搜索(包括A*算法等); 搜索通常会用到的知识点:状态压缩(位压缩,利用hash思想压缩)。

poj3468(线段树成段更新模板题)

题意:包括两个操作:1、将[a.b]上的数字加上v;2、查询区间[a,b]上的和 下面的介绍是下解题思路: 首先介绍  lazy-tag思想:用一个变量记录每一个线段树节点的变化值,当这部分线段的一致性被破坏我们就将这个变化值传递给子区间,大大增加了线段树的效率。 比如现在需要对[a,b]区间值进行加c操作,那么就从根节点[1,n]开始调用update函数进行操作,如果刚好执行到一个子节点,

C++11第三弹:lambda表达式 | 新的类功能 | 模板的可变参数

🌈个人主页: 南桥几晴秋 🌈C++专栏: 南桥谈C++ 🌈C语言专栏: C语言学习系列 🌈Linux学习专栏: 南桥谈Linux 🌈数据结构学习专栏: 数据结构杂谈 🌈数据库学习专栏: 南桥谈MySQL 🌈Qt学习专栏: 南桥谈Qt 🌈菜鸡代码练习: 练习随想记录 🌈git学习: 南桥谈Git 🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈🌈�