python实现全排列代码(回溯、深度优先搜索)


Posted in Python onFebruary 26, 2020

从n个不同元素中任取m(m≤n)个元素,按照一定的顺序排列起来,叫做从n个不同元素中取出m个元素的一个排列。当m=n时所有的排列情况叫全排列。

公式:全排列数f(n)=n!(定义0!=1)

1 递归实现全排列(回溯思想)

1.1 思想

举个例子,比如你要对a,b,c三个字符进行全排列,那么它的全排列有abc,acb,bac,bca,cba,cab这六种可能就是当指针指向第一个元素a时,它可以是其本身a(即和自己进行交换),还可以和b,c进行交换,故有3种可能,当第一个元素a确定以后,指针移向第二位置,第二个位置可以和其本身b及其后的元素c进行交换,又可以形成两种排列,当指针指向第三个元素c的时候,这个时候其后没有元素了,此时,则确定了一组排列,输出。但是每次输出后要把数组恢复为原来的样子。

python实现全排列代码(回溯、深度优先搜索)

1.2 python实现

def permutations(arr, position, end):
  if position == end:
    print(arr)
  else:
    for index in range(position, end):
      arr[index], arr[position] = arr[position], arr[index]
      permutations(arr, position + 1, end)
      arr[index], arr[position] = arr[position], arr[index] # 还原到交换前的状态,为了进行下一次交换
 
 
arr = [1, 2, 3, 4]
permutations(arr, 0, len(arr))

2 深度优先搜索(DFS)实现全排列

2.1 思想

定义全排列问题:输入一个长度为n的列表arr,输出arr的全排列。

(1)首先可以确定的是,每一种全排列的结果中包含的列表长度均是n。想象面前有n个空盒子,现在要把这n个数放到这些空盒子里去,每个盒子只能放一个数。那么第一个盒子中可以放的选择是n种,可以使用一个循环来逐个尝试。

for index in range(0, len(arr)):
temp[position] = arr[index]

(2)第一个盒子放完后,就该往第二个盒子里放了。假设第一个盒子里放的是arr的第一个数,那么第二个盒子就只能放第2~n个数了(不能重复)。为此引入visit列表用来标记arr中哪些数字被使用过了。初始化:

visit = [True, True, True, True]

这样,当第一个位置已经使用过时,就在visit里做标记:visit = [False, True, True, True]

因此放第一个盒子的代码可以改写如下:

for index in range(0, len(arr)):
    if visit[index] == True:
      temp[position] = arr[index]
      visit[index] = False

(3)当第k个盒子处理完毕后,处理下一个盒子直接调用dfs(k+1)即可,也就是递归调用。解决了当下该如何做,下一步也就知道怎么做了。

(4)递归调用的一定要注意的问题是递归调用的出口,否则循环调用下去程序会崩溃无法运行。在这个问题中什么时候结束递归调用呢?答案是当这n个盒子都放满了,即处理到第n+1个盒子时结束调用,同时输出此时的排列结果。

2.2 python实现

visit = [True, True, True, True]
temp = ["" for x in range(0, 4)]
 
 
def dfs(position):
  # 递归出口
  if position == len(arr):
    print(temp)
    return
  # 递归主体
  for index in range(0, len(arr)):
    if visit[index] == True:
      temp[position] = arr[index]
      visit[index] = False # 试探 
      dfs(position + 1)
      visit[index] = True # 回溯。非常重要
 
 
arr = [1, 2, 3, 4]
dfs(0)

注释了“非常重要”的语句是不能省略的,省略后仅出现[1, 2, 3, 4]一条结果。dfs(k+1)前后的两条语句分别称之为试探和回溯。

3 combination和permutations函数的区别

permutations方法重在排列:

import itertools
n=3
a=[str(i) for i in range(n)]
s=""
s=s.join(a)
for i in itertools.permutations(s,n):
  print (''.join(i))
 
# 结果  
012
021
102
120
201
210

combinations方法重在组合:

import itertools
n=3
a=[str(i) for i in range(n)]
s=""
s=s.join(a)
for i in itertools.combinations(s,n):
  print (''.join(i))
 
# 结果  
012

以上这篇python实现全排列代码(回溯、深度优先搜索)就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python 远程统计文件代码分享
May 14 Python
Python数据类型学习笔记
Jan 13 Python
Python中函数参数设置及使用的学习笔记
May 03 Python
详解python进行mp3格式判断
Dec 23 Python
Mac 上切换Python多版本
Jun 17 Python
Python求两个圆的交点坐标或三个圆的交点坐标方法
Nov 07 Python
Python获取网段内ping通IP的方法
Jan 31 Python
Python3调用百度AI识别图片中的文字功能示例【测试可用】
Mar 13 Python
selenium+python自动化测试环境搭建步骤
Jun 03 Python
python flask框架实现传数据到js的方法分析
Jun 11 Python
python 模拟创建seafile 目录操作示例
Sep 26 Python
基于jupyter代码无法在pycharm中运行的解决方法
Apr 21 Python
python GUI库图形界面开发之PyQt5 Qt Designer工具(Qt设计师)详细使用方法及Designer ui文件转py文件方法
Feb 26 #Python
python 使用递归回溯完美解决八皇后的问题
Feb 26 #Python
基于Python数据结构之递归与回溯搜索
Feb 26 #Python
深度学习入门之Pytorch 数据增强的实现
Feb 26 #Python
Python基于Dlib的人脸识别系统的实现
Feb 26 #Python
python 回溯法模板详解
Feb 26 #Python
python实现信号时域统计特征提取代码
Feb 26 #Python
You might like
ThinkPHP令牌验证实例
2014/06/18 PHP
PHP的Socket通信之UDP通信实例
2015/07/02 PHP
php计算多个集合的笛卡尔积实例详解
2017/02/16 PHP
PHP实现下载远程图片保存到本地的方法
2017/06/19 PHP
jquery.validate使用攻略 第二部
2010/07/01 Javascript
jQuery 1.5最新版本的改进细节分析
2011/01/19 Javascript
2012年开发人员的16款新鲜的jquery插件体验分享
2012/12/28 Javascript
探讨jQuery的ajax使用场景(c#)
2013/12/03 Javascript
JS正则表达式修饰符中multiline(/m)用法分析
2016/12/27 Javascript
vue2.0与bootstrap3实现列表分页效果
2017/11/28 Javascript
layui弹出层按钮提交iframe表单的方法
2018/08/20 Javascript
jQuery实现当拉动滚动条到底部加载数据的方法分析
2019/01/24 jQuery
优雅的处理vue项目异常实战记录
2019/06/05 Javascript
Element Steps步骤条的使用方法
2020/07/26 Javascript
[01:05]主宰至宝剑心之遗
2017/03/16 DOTA
python实现给字典添加条目的方法
2014/09/25 Python
python实现的文件夹清理程序分享
2014/11/22 Python
Python实现选择排序
2017/06/04 Python
Python对列表中的各项进行关联详解
2017/08/15 Python
python使用正则表达式的search()函数实现指定位置搜索功能
2017/11/10 Python
python计算两个地址之间的距离方法
2018/06/09 Python
pygame游戏之旅 添加icon和bgm音效的方法
2018/11/21 Python
对python同一个文件夹里面不同.py文件的交叉引用方法详解
2018/12/15 Python
Python 类的私有属性和私有方法实例分析
2019/09/29 Python
Python 窗体(tkinter)下拉列表框(Combobox)实例
2020/03/04 Python
Python Opencv轮廓常用操作代码实例解析
2020/09/01 Python
解锁canvas导出图片跨域的N种姿势小结
2019/01/24 HTML / CSS
惠普香港官方商店:HP香港
2019/04/30 全球购物
大宝sod蜜广告词
2014/03/21 职场文书
中学生学雷锋演讲稿
2014/04/26 职场文书
小学生倡议书范文
2014/05/13 职场文书
小学趣味运动会加油稿
2014/09/25 职场文书
公司租车协议书
2015/01/29 职场文书
大学生志愿者心得体会
2016/01/15 职场文书
观看《杨善洲》宣传教育片心得体会
2016/01/23 职场文书
5个pandas调用函数的方法让数据处理更加灵活自如
2022/04/24 Python