a 为您提供了大小为 a 的木板。板上有 n 个组件,这些组件必须以尽可能短的导线长度连接到板的边缘。
电线是直的,不能重叠。
找到算法以将这些组件连接到具有这些约束的边缘。
约束条件:
时间:1秒
空间:无限
1 <= a <= 30
1 <= n <= 38
示例:
Input: 4 3 2 1 2 3 3 3 Output: 5 DOWN UP UP
我发现了一种递归,让我用上面提供的数据来说明这个想法。
我有一个n位掩码,其中第i个位置的extension Array where Element == Option {
// No idea how to do this
}
表示我们考虑了此组件,而1
没有考虑。
当我开始递归时,我有n个:
111 / | \ / | \ 011 101 110 / \ / \ / \ 001 010 001 100 010 100
当我到达最低级别时,我只有一个0
。我找到了针对这个简单问题的最佳解决方案(最简单的方法),然后将其用于进一步的计算。
但是,我有一个问题,这个最佳解决方案可能导致重叠。
答案 0 :(得分:1)
就目前而言,我无法真正看到一种比branch and bound方法更好或更聪明的解决方案。它在某种程度上类似于您的建议,但没有多余的计算。
在这里,它被简单地描述为pythonic伪代码:
def BnB(grid, components):
queue = new_priority_queue() # classic priority queue
empty_sol = [None for i in range(len(components))] # we create an 'empty' solution
queue.push((0, 0, empty_sol)) # we push an initial empty solution on the queue (a tuple total len, index, solution)
best_length_so_far = infinite # we keep track of the best solution seen so far
best_sol_so_far = None
while not queue.is_empty():
length, index, solution = queue.pop()
if index == len(components): # it is a feasible solution
if best_len_so_far > length:
best_len_so_far = length
best_sol_so_far = solution
elif length < best_len_so_far:
# check if components[index] can have its wire 'DOWN'
if can_put_wire(grid, components, index, 'DOWN'):
length_to_add = path_len(grid, component, index, 'DOWN')
new_sol = copy(solution)
new_sol[index] = 'DOWN'
queue.push((length + length_to_add, index + 1, new_sol))
# do the same thing for the other directions
if can_put_wire(grid, components, index, 'UP'):
....
if can_put_wire(grid, components, index, 'LEFT'):
....
if can_put_wire(grid, components, index, 'RIGHT'):
....
return best_sol_so_far
对解决方案树的探索将取决于您如何在队列上设置优先级。选择要考虑的组件(而不是按照上面的代码中的顺序进行选择)也可能有助于更快地找到解决方案。 这将是无效的(时间复杂度随组件数量而变),但是可以找到解决方案。
另一种可能性是使用ILP(整数线性规划)来解决该问题。用线性约束可以很容易地描述它,并且可以享受LP解算器提供的所有优化。