POJ3076 Sudoku

  • 本题为16*16宫格
  • 剪枝见代码
 #include <cstdio>
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
const int N=; #define res register int
int map[N][N];
unsigned short t[N][N];
//table[i,j](二进制)表示(i,j)可以填的数,0可填,1不可填
int filled(); inline void my_fill(int x,int y,int a)//(x,y)填a
{
filled++;
map[x][y]=a;
t[x][y] |=<<(a-);
for(res i= ; i< ; i++)
t[x][i] |=<<(a-),
t[i][y] |=<<(a-);
int r=x/*,c=y/*;//(r,c)表示(x,y)所在的16宫格的左上角的格子,(从(0,0)开始)
for(res i= ; i< ; i++)
for(res j= ; j< ; j++) t[r+i][j+c] |=<<(a-);
} //判断x中0的个数是否只有1个
int count_zero(unsigned short x)
{
int p(-);
for(int i=;x;i++)
{
if(x&==)
{
if(p!=-) return -;
p=i;
}
x>>=;
}
return p;
} //第x行,数字k+1,返回>0表示唯一可填的k+1的位置,-1表示有多个可以填的位置或已经填过,-2不能填
inline int col(int x,int k)
{
int p(-);
for(res y= ; y< ; y++)
{
if(map[x][y]==k+) return -;//已经填过
if(map[x][y]>) continue;
if((t[x][y]&(<<k))==)
{
if(p!=-) return -;//多次出现
p=y;
}
}
if(p!=-) return p;
return -;
} //第y列,数字k
inline int row(int y,int k)
{
int p=-;
for(res x= ; x< ; x++)
{
if(map[x][y]==k+) return -;
if(map[x][y]>) continue;
if((t[x][y]&(<<k))==)
{
if(p!=-) return -;
p=x;
}
}
if(p!=-) return p;
return -;
} inline void grid(int r,int c,int k,int &x,int &y)
//以(r,c)为左上角的16宫格,数字k+1,(x,y)为唯一可填坐标[
{
x=-;
for(res i= ; i< ; i++)
for(res j= ; j< ; j++)
{
if(map[r+i][c+j]==k+) {x=-; return ;}
if(map[r+i][c+j]>) continue;
if((t[r+i][c+j]&(<<k))==)
{
if(x!=-) {x=-; return ;}
x=i,y=j;
}
}
} inline int count_1(unsigned short x) {
int tmp();
while(x) {
if(x&) tmp++;
x>>=;
}
return tmp;
} bool search()
{
if(filled==) return true;
//先看是否有能确定的格子
for(res x= ; x< ; x++)
for(res y= ; y< ; y++)
{
if(map[x][y]>) continue;
int k=count_zero(t[x][y]);
if(k!=-) my_fill(x,y,k+);
}
for(res x= ; x< ; x++)
for(res k= ; k< ; k++)
{
int y=col(x,k);
if(y==-) return false;
if(y!=-) my_fill(x,y,k+);
}
for(res y= ; y< ; y++)
for(res k= ; k< ; k++)
{
int x=row(y,k);
if(x==-) return false;
if(x!=-) my_fill(x,y,k+);
}
for(res r= ; r< ; r+=)
for(res c= ; c< ; c+=)
for(res k= ; k< ; k++)
{
int x,y;
grid(r,c,k,x,y);
if(x==-) return false;
if(x!=-) my_fill(r+x,c+y,k+);
}
if(filled==) return true;
int t_filled(filled);
int t_map[N][N];
unsigned short t_t[N][N];
for(res i= ; i< ; i++)
for(res j= ; j< ; j++)
t_map[i][j]=map[i][j],
t_t[i][j]=t[i][j];
//找可能情况最少的格子来枚举
int mx,my,mn=;
for(res i= ; i< ; i++)
for(res j= ; j< ; j++)
{
if(map[i][j]>) continue;
int r=-count_1(t[i][j]);
//未确定的
if(r<mn)
{
mn=r; mx=i; my=j;
}
}
for(res k= ; k< ; k++)
if((t[mx][my]&<<k)==)
{
my_fill(mx,my,k+);
if(search()) return true;
filled=t_filled;
for(res i= ; i< ; i++)
for(res j= ; j< ; j++)
map[i][j]=t_map[i][j],
t[i][j]=t_t[i][j];
}
return false;
} char ar[N];
int main()
{
while()
{
filled=;
memset(map,,sizeof(map)); memset(t,,sizeof(t));
for(int i= ; i< ; i++)
{
if(scanf("%s",ar)==EOF) return ;
for(int j= ; j< ; j++)
if(ar[j]!='-') my_fill(i,j,ar[j]-'A'+);
}
search();
for(res i= ; i< ; i++)
{
for(res j= ; j< ; j++) printf("%c",map[i][j]+'A'-);
puts("");
}
puts("");
}
return ;
}

POJ3076 Sudoku的更多相关文章

  1. POJ3076 Sudoku 舞蹈链 DLX

    欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目(传送门) 题意概括 给出一个残缺的16*16数独,求解. 题解 DLX + 矩阵构建  (两个传送门) 学完这个之后,再 ...

  2. 【转】Dancing Links题集

    转自:http://blog.csdn.net/shahdza/article/details/7986037 POJ3740 Easy Finding [精确覆盖基础题]HUST1017 Exact ...

  3. dancing links 题集转自夏天的风

    POJ3740     Easy Finding [精确覆盖基础题] HUST1017    Exact cover [精确覆盖基础] HDOJ3663 Power Stations [精确覆盖] Z ...

  4. Sudoku(POJ2676/3074)

    Sudoku is one of the metaphysical techniques. If you understand the essence of it, you will have the ...

  5. Leetcode 笔记 36 - Sudoku Solver

    题目链接:Sudoku Solver | LeetCode OJ Write a program to solve a Sudoku puzzle by filling the empty cells ...

  6. [LeetCode] Sudoku Solver 求解数独

    Write a program to solve a Sudoku puzzle by filling the empty cells. Empty cells are indicated by th ...

  7. [LeetCode] Valid Sudoku 验证数独

    Determine if a Sudoku is valid, according to: Sudoku Puzzles - The Rules. The Sudoku board could be ...

  8. LeetCode 36 Valid Sudoku

    Problem: Determine if a Sudoku is valid, according to: Sudoku Puzzles - The Rules. The Sudoku board ...

  9. 【leetcode】Valid Sudoku

    题目简述: Determine if a Sudoku is valid, according to: Sudoku Puzzles - The Rules. The Sudoku board cou ...

随机推荐

  1. UITextView设置占位文字

    这里只介绍一种,这种方便扩展,可以占位文字颜色. 我们继承一个UITextView: #import <UIKit/UIKit.h> @interface MyTextView : UIT ...

  2. SpringBoot28 RabbitMQ知识点、Docker下载RabbitMQ、SpringBoot整合RabbtiMQ

    1 RabbitMQ知识点 1.1 整体架构图 消息生产者将消息投递到exchange中,exchange会以某种路由机制将生产者投递的消息路由到queue中,消息消费者再从queue中获取消息进行消 ...

  3. loadrunner中回放log看不到参数替代后具体数值

    1.打开run-time settings,找到 log - always send messages,选择 extended log--parameter substitution.

  4. 解决ImportError: libmysqlclient_r.so.16: cannot open shared object file-乾颐堂

    在开发一个python项目是,需要用到mysql,但是, 安装完mysql-python后import加载模块提示以下错误: ImportError: libmysqlclient_r.so.16: ...

  5. 详解Python垃圾回收机制

    http://www.qytang.com/cn/list/28/417.htmhttp://www.qytang.com/cn/list/28/416.htmhttp://ww 引用计数 Pytho ...

  6. Spring Boot☞ 多数据源配置(二):Spring-data-jpa

    效果图: 代码区: package com.wls.integrateplugs.datasource; import org.springframework.beans.factory.annota ...

  7. Spring Data JPA初使用 *****重要********

    Spring Data JPA初使用 我们都知道Spring是一个非常优秀的JavaEE整合框架,它尽可能的减少我们开发的工作量和难度. 在持久层的业务逻辑方面,Spring开源组织又给我们带来了同样 ...

  8. 数据库SQL优化大总结之 百万级数据库优化方案(转)

    出处:http://www.cnblogs.com/yunfeifei/p/3850440.htm 网上关于SQL优化的教程很多,但是比较杂乱.近日有空整理了一下,写出来跟大家分享一下,其中有错误和不 ...

  9. QtCreator下QML翻译

    首先打开.pro工程文件,在文件中添加文本段:TRANSLATIONS = testTranslate_zh.ts 在pro右键,单击再次弹出命令提示,如图 在命令行中,输入lupdate testT ...

  10. 【转载】redis优化配置和redis.conf说明

    转载地址:http://blog.csdn.net/luozhonghua2014/article/details/40568707?utm_source=tuicool&utm_medium ...