python3.6数独问题的解决


Posted in Python onJanuary 21, 2019

算法比较暴力,直接用穷举的方式一个一个去试,所以程序运行时间会比较长,运行时间视数独而定。
不过从一开始到运行成功,整个过程却是一波三折,设计算法就花了不少时间,然后就是不断地去调试,找bug。刚开始的时候为了省事直接在sudoku类中递归调用blank,但是老哥还是too young too simple,sometimes navie,计算量实在是太大了,后面编译器直接抛出 “RecursionError: maximum recursion depth exceeded while calling a Python object” 超过最大递归深度的错误。在把递归深度改到100000之后,又出现了堆栈溢出问题。当然,解决办法也是相当地暴力:把递归放入while循环中,一旦符合条件就直接exit(0),整个程序直接gg,然后退出结束。
当然,算法还可以再优化一下,可以不用那么暴力,先列出可能的值然后再填入,这样可以大大缩小整个程序的运行时间,但是……懒得优化了,就这样吧,又不是不能用(笑~)。

运行结果:

python3.6数独问题的解决

再试一个其他的数独:

python3.6数独问题的解决

这回就快得多了,11秒就完成了,比第一个数独不知高到哪里去了

代码如下所示:

import copy
import time

t1=time.time()
origin = [[8, 0, 0, 0, 0, 0, 0, 0, 0],
  [0, 0, 3, 6, 0, 0, 0, 0, 0],
  [0, 7, 0, 0, 9, 0, 2, 0, 0],
  [0, 5, 0, 0, 0, 7, 0, 0, 0],
  [0, 0, 0, 0, 4, 5, 7, 0, 0],
  [0, 0, 0, 1, 0, 0, 0, 3, 0],
  [0, 0, 1, 0, 0, 0, 0, 6, 8],
  [0, 0, 8, 5, 0, 0, 0, 1, 0],
  [0, 9, 0, 0, 0, 0, 4, 0, 0]]

class sudoku:
 def debug(self): # 调试
 for list in origin:
  print(list)
 print("\n")

 def check_repetition(self,list):#判断表中是否有重复值,0除外
 flag=0
 for i in range(1,10):
  if list.count(i)>=2:
  return 1
  else:
  flag=flag+1
 if flag==9:
  return 0

 def check_row(self,row):#检测横向是否有重复值,无则为返回0,有则返回1
 list = origin[row] # 横向
 r1 = self.check_repetition(list)
 if r1 == 0:
  return 0
 else :
  return 1

 def check_column(self,column):#检测纵向是否重复值,无则为返回0,有则返回1
 list = [] # 纵向
 for num in origin:
  list.append(num[column])
 r2 = self.check_repetition(list)
 if r2==0:
  return 0
 else:
  return 1

 def check_square(self,x,y):#检测九宫格是否有重复值,无则为返回0,有则返回1
 x,y=y,x
 if x>=9 or y>=9:
  return
 square = []#九宫格
 for i in range(0+y//3*3, 3+y//3*3):
  for j in range(0+x//3*3, 3+x//3*3):
  square.append(origin[i][j])
 r3 = self.check_repetition(square)
 if r3==0:
  return 0
 else:
  return 1

 def check(self,x,y):#检测是否有重复值,无则为0,有则不为0
 r1 = self.check_row(x)
 r2 = self.check_column(y)
 r3 = self.check_square(x, y)
 result=r1+r2+r3
 return result

 def get_next(self): # 获得下一个空值,返回row,column值
 i = 0
 for list in origin:
  try: # 当0不在列表中时,跳过
  column = list.index(0)
  row = origin.index(list)
  res = (row, column)
  return res
  except ValueError:
  i = i + 1
  if i == 9:
   t2=time.time()
   print("总用时={}".format(t2 - t1))
   exit(0)

 def poi(self,row, column): # 位置修正
 if row == 0 and column == -1:
  return
 if row == 8 and column == 9:
  return
 if column == -1:
  column = 8
  row = row - 1
 if column == 9:
  column = 0
  row = row - 1
 return (row, column)

 def get_last(self,row, column):
 origin[row].insert(column, 0)
 origin[row].pop(column + 1)
 column = column - 1 # 获得上一个已填值的行、列位置
 row, column = self.poi(row, column)#位置修正
 r = origin[row][column] * compare[row][column]
 while r != 0:
  column = column - 1
  row, column = self.poi(row, column)
  r = origin[row][column] * compare[row][column]
 return (row, column)

 def blank(self):
 try:
  row,column=self.get_next()
 except TypeError:#已填完
  exit(0)
 j=0
 flag=0
 for i in range(1,10):
  origin[row].insert(column,i)
  origin[row].pop(column+1)
  self.debug()
  r = self.check(row, column)
  if r==0:#无重复值
  return
  else:
  j = j + 1
  if j==9:
   flag=1
   break
 if flag==1:
  row, column = self.get_last(row, column)
  value=origin[row][column]
  self.debug()
  while value == 9:
  row, column = self.get_last(row, column)
  value = origin[row][column]
  self.debug()
  while value<9:
  for k in range(value+1,10):
   origin[row].insert(column, k)
   origin[row].pop(column + 1)
   self.debug()
   r=self.check(row,column)
   if r!=0:#有重复
   if k==9:
    row, column = self.get_last(row, column)
    value=origin[row][column]
    self.debug()
    while value==9:
    row, column = self.get_last(row, column)
    value = origin[row][column]
    self.debug()
    break
   else:
   return

if __name__=="__main__":
 compare = copy.deepcopy(origin)
 sudoku = sudoku()
 while 1:
 sudoku.blank()

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
Python Deque 模块使用详解
Jul 04 Python
Python中splitlines()方法的使用简介
May 20 Python
python使用os.listdir和os.walk获得文件的路径的方法
Dec 16 Python
python使用socket 先读取长度,在读取报文内容示例
Sep 26 Python
Python 中list ,set,dict的大规模查找效率对比详解
Oct 11 Python
selenium 多窗口切换的实现(windows)
Jan 18 Python
python的reverse函数翻转结果为None的问题
May 11 Python
python如何写出表白程序
Jun 01 Python
python datetime时间格式的相互转换问题
Jun 11 Python
pytorch 如何使用batch训练lstm网络
May 28 Python
Python实现8种常用抽样方法
Jun 27 Python
python3实现常见的排序算法(示例代码)
Jul 04 Python
解决python给列表里添加字典时被最后一个覆盖的问题
Jan 21 #Python
对python列表里的字典元素去重方法详解
Jan 21 #Python
在Python中字典根据多项规则排序的方法
Jan 21 #Python
详解opencv Python特征检测及K-最近邻匹配
Jan 21 #Python
pycharm远程开发项目的实现步骤
Jan 20 #Python
对python中类的继承与方法重写介绍
Jan 20 #Python
python 格式化输出百分号的方法
Jan 20 #Python
You might like
在PHP中使用模板的方法
2008/05/24 PHP
php chr() ord()中文截取乱码问题解决方法
2008/09/08 PHP
Thinkphp实现自动验证和自动完成
2015/12/19 PHP
Codeigniter中集成smarty和adodb的方法
2016/03/04 PHP
Yii2.0 模态弹出框+ajax提交表单
2016/05/22 PHP
PHP7.1新功能之Nullable Type用法分析
2016/09/26 PHP
PHP判断是否是微信打开还是浏览器打开的方法
2019/02/27 PHP
jquery imgareaselect 使用利用js与程序结合实现图片剪切
2009/07/30 Javascript
document.forms[].submit()使用介绍
2014/02/19 Javascript
按钮接受回车事件的三种实现方法
2014/06/06 Javascript
js读取cookie方法总结
2014/10/31 Javascript
JavaScript前端开发之实现二进制读写操作
2015/11/04 Javascript
大型JavaScript应用程序架构设计模式
2016/06/29 Javascript
结合代码图文讲解JavaScript中的作用域与作用域链
2016/07/05 Javascript
es6新特性之 class 基本用法解析
2018/05/05 Javascript
使用javascript做在线算法编程
2018/05/25 Javascript
angularJs利用$scope处理升降序的方法
2018/10/08 Javascript
原生JS实现轮播图效果
2018/10/12 Javascript
Vue创建头部组件示例代码详解
2018/10/23 Javascript
JavaScript私有变量实例详解
2019/01/24 Javascript
浅谈vue中组件绑定事件时是否加.native
2019/11/09 Javascript
js实现三角形粒子运动
2020/09/22 Javascript
[02:00]DOTA2英雄COSPLAY闹市街头巡游助威2015国际邀请赛
2015/08/02 DOTA
python正则表达式去掉数字中的逗号(python正则匹配逗号)
2013/12/25 Python
对python修改xml文件的节点值方法详解
2018/12/24 Python
python 字典的打印实现
2019/09/26 Python
浅析Django 接收所有文件,前端展示文件(包括视频,文件,图片)ajax请求
2020/03/09 Python
python 解决mysql where in 对列表(list,,array)问题
2020/06/06 Python
英国工作场所设备购买网站:Slingsby
2019/05/03 全球购物
八一建军节营销活动方案
2014/08/31 职场文书
信用卡工资证明格式
2014/09/13 职场文书
幼儿园五一劳动节活动总结
2015/02/09 职场文书
因家庭原因离职的辞职信范文
2015/05/12 职场文书
新员工入职感想
2015/08/07 职场文书
公司团队口号霸气押韵
2015/12/24 职场文书
详解NumPy中的线性关系与数据修剪压缩
2022/05/25 Python