我不知道如何创建一个给出列表列表的函数,例如:
[[0,0,1,1],[0,0,1,0],[1,1,0,1],[0,0,0,0]]
表示第一个可以转到第二个和第三个,节点2可以转到第三个,第三个节点可以转到第一个,第二个和第四个,第四个节点不能转到任何一个一,所以,我想在haskell中创建一个函数,如果我找到一个哈密尔顿路径,那个列表列表(只有0和1)返回一个Bool,这意味着你可以访问所有节点< /强>
答案 0 :(得分:2)
哈密尔顿路径是通过图表的路径,它只访问每个节点一次。找到一个最简单,最天真的方法是实际尝试所有可能的节点排列,并为每个这样的路径检查它是否是哈密顿量。
为了编写这样的功能,尝试分解问题。
首先编写一个函数,检查两个节点之间是否存在边缘:hasEdge :: [[Int]] -> Int -> Int -> Bool
。
另一个有用的函数将检查路径是哈密顿量:isHamiltonian :: [[Int]] -> [Int] -> Bool
。假设第二个参数是节点编号列表,其中每个节点只有一个,因此您只需要验证列表中的每个后续对都代表图中的边。
现在剩下的就是生成列表[0..(length ps - 1)]
的所有排列,并检查是否满足isHamiltonian
谓词。您可以在此处从Data.List
中找到函数permutations
非常有用。
这种方法显然会非常缓慢,但对于NP难问题而言,这是一种预期。无论如何,在实施更好的算法之前,这可能是一个好的开始。