回溯全排列

本文详细解析了回溯算法在全排列问题中的应用。通过深度优先搜索解空间,逐步构建并检查每一步的可能性,直到找到所有可能的排列。文章介绍了状态节点的概念,并以n=3为例,展示了解空间的搜索图,阐述了如何扩展和回溯节点以生成所有排列。在编程实现中,使用PTState类记录排列状态,通过CanPlace、Place和Remove函数实现回溯逻辑,利用m_used数组避免重复排列。
摘要由CSDN通过智能技术生成

回溯的实质是在问题的解空间进行深度优先搜索。DFS是个图的算法,但是回溯算法中的图在哪里呢?我们把解空间中的一个解状态当成一个节点,由于解空间非常庞大,所以这个图也就大到无法想象了。


举个例子吧,比如全排列问题,对于n个元素进行全排列,一共有n!种可能,比如n=9时,一共有9! = 362880种排列。初始化,我们什么都没有,定义如下状态

#define PT_SIZE 9
class PTState
{
	int m_solution[PT_SIZE];
	int m_arranged;
};

其中m_arranged表示已经在m_solution中排列的数字,刚开始时啥都没做,当然是m_arranged为0啦,而m_solution这个数组是用来放要排列的数字的,比如

123456789对应于m_solution[i] = i + 1


那么接下来要做啥呢?当然是开始排第一个数了,也就是要填m_solution[0]啦,这时你有多少种选择呢?嗯,当然是1, 2, 3, 4, 5 ,6, 7,8,9种,这还要说吗?那么先尝试谁呢?

从小到小依次填好了。


下面这个图是n=3时的解空间搜索图,其中白色的节点是初始节点,一个数都没填,第一行全是问号,第二行有个标记,表示还没有排列一个数。当第一位选1的时,节点变成了紫色,此时m_arranged = 1, 还剩两个数没有填。这时填第二个数时&#

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值