用于枚举完整图的哈密顿循环的算法(循环、反向、环绕或重复不计算在内的排列)
Algorithm for Enumerating Hamiltonian Cycles of a Complete Graph (Permutations where loops, reverses, wrap-arounds or repeats don't count)
我想生成一个完整的无向图的所有哈密顿循环(循环和反向计为重复项的集合的排列,并且被排除在外)。
例如,{1,2,3} 的排列是
标准排列:
1,2,3
1,3,2
2,1,3
2,3,1
3,1,2
3,2,1
我希望程序/算法为我打印的内容:
1,2,3
由于 321 只是 123 向后,312 只是 123 旋转一个地方,等等。
我看到很多关于给定集合具有的这些循环数的讨论,以及查找图是否具有哈密顿循环的算法,但没有关于如何在完整的无向图中枚举它们(即一组数字可以先于或后随集合中的任何其他数字)。
我真的很想要一个算法或C++代码来完成这项任务,或者如果你能引导我到哪里有关于这个主题的材料。谢谢!
您可以对输出进行一些限制,以消除不需要的排列。假设我们要排列数字 1, ..., N。为了避免某些特殊情况,假设 N> 2。
为了消除简单的旋转,我们可以要求第一名是 1。这是真的,因为任意排列总是可以旋转成这种形式。
为了消除反转,我们可以要求第二位的数字必须小于最后一位的数字。这是真的,因为从从 1 开始的两个相互颠倒的排列中,正好有一个具有这个属性。
因此,一个非常简单的算法可以枚举所有排列并省略无效排列。当然,也有优化的可能。例如,在生成步骤中可以轻松避免不以 1 开头的排列。
一种超级懒惰的方法来检查路径是否与在循环中的不同点开始的路径相同(IE,同一循环或同一循环的反面是这样的:
1:按照惯例,确定所有循环将从最低顶点数开始,并沿两个相邻序数中较低值的方向继续。
因此,上述所有路径都将以相同的方式描述。
第二,其他有用的信息在这里:
如果要检查两条路径是否相同,可以将其中一条与其自身连接起来,并检查它是否包含第二条路径或第二条路径的反向路径。
那是
1 2 3 1 2 3
包含上述所有路径或其反向路径。 由于找到所有哈密顿循环的过程似乎比该算法的轻微低效率要慢得多,我觉得我可以把它扔进:)
- 当 A 在 for 循环中调用函数 B 时,如何计算函数 A 的空间复杂度?
- 如何编写计算功率的循环
- 在循环条件 i<sqrtN(预先计算)和 i*i<N 中,C++哪个更有效?
- 如果代码包含多个复杂度循环,如何计算复杂度
- C++在不使用pow或循环的情况下计算一个数字的幂
- 计算递归和时的无限循环
- 使用与 openmp C++并行的循环计算矩阵中每一行的最小值
- getline() 在 while 循环条件中如何计算为真或假?
- 为什么 g++ 将计算拉入热循环
- 计算使用 C++ std 函数而不是 for 循环的大 O
- 使用一个WALE循环计算AVG测试得分
- C++ (for) 循环:计算 y=n/(n+1)
- (C++)使用while循环计算平均数
- 尝试使用for循环计算Pi只给出3
- 基本的依偎循环计算1 - 239之间的质数,包括
- 循环计算矩形面积的公式
- c++ 11基于范围的for()循环计算一次或多次
- 使用while循环计算前n个斐波那契数的程序
- 使用while循环计算数学常数e
- 用泰勒方法和循环计算圆周率