简体   繁体   English

如何在python中解决5x5矩阵中的未知数

[英]How to solve for unknowns in a 5x5 matrix in python

Here is a 5x5 matrix, with all cells unknown, it looks something like this:这是一个 5x5 矩阵,所有单元格都未知,它看起来像这样:

A1+B1+C1+D1+E1| 1
A2+B2+C2+D2+E2| 0
A3+B3+C3+D3+E3| 1
A4+B4+C4+D4+E4| 3
A5+B5+C5+D5+E5| 2
_______________
2  1  2  1  1

So, the summation of rows can be seen on the right, and the summation of columns can be seen on the bottom.因此,可以在右侧看到行的总和,在底部可以看到列的总和。 The solution can only be 0 or 1, and as an example here is the solution to the specific one I have typed out above:解决方案只能是 0 或 1,作为一个例子,这里是我在上面输入的特定解决方案的解决方案:

0+0+1+0+0| 1
0+0+0+0+0| 0
1+0+0+0+0| 1
1+1+0+0+1| 3
0+0+1+1+0| 2
____________
2 1 2 1 1

As you can see, summing the rows and columns gives the results on the right and bottom.如您所见,对行和列求和得出右侧和底部的结果。 My question: How would you go about entering the original matrix with unknowns and having python iterate each cell with 0 or 1 until the puzzle is complete?我的问题:您将如何使用未知数输入原始矩阵并让 python 用 0 或 1 迭代每个单元格,直到拼图完成?

You don't really need a matrix -- just use vectors (tuples) of length 25. They can represent 5x5 matrices according to the following scheme:您实际上并不需要矩阵——只需使用长度为 25 的向量(元组)。它们可以根据以下方案表示 5x5 矩阵:

0  1  2  3  4
5  6  7  8  9
10 11 12 13 14
15 16 17 18 19
20 21 22 23 24

These are the indices of such tuples.这些是这些元组的索引。 Note that the row and column of an index can be obtained from the function divmod .请注意,可以从函数divmod获得索引的行和列。

You can use product from itertools to iterate over the 2**25 possible ways of filling in the matrix.您可以使用itertools product来迭代 2**25 种可能的矩阵填充方式。

These ideas lead to the following code:这些想法导致了以下代码:

from itertools import product

#nxn matrices will be represented by tuples of length n**2,
#in row-major order
#the following function caluculates row and column sums:

def all_sums(array,n):
    row_sums = [0]*n
    col_sums = [0]*n
    for i,x in enumerate(array):
        q,r = divmod(i,n)
        row_sums[q] += x
        col_sums[r] += x
    return row_sums, col_sums

#in what follows, row_sums, col_sums are lists of target values

def solve_puzzle(row_sums, col_sums):
    n = len(row_sums)
    for p in product(range(2),repeat = n*n):
        if all_sums(p,n) == (row_sums, col_sums):
            return p
    return "no solution"

solution = solve_puzzle([1,0,1,3,2],[2,1,2,1,1])
for i in range(0,25,5):
    print(solution[i:i+5])

Output:输出:

(0, 0, 0, 0, 1)
(0, 0, 0, 0, 0)
(0, 0, 0, 1, 0)
(1, 1, 1, 0, 0)
(1, 0, 1, 0, 0)

In this case brute-force was feasible.在这种情况下,蛮力是可行的。 If you go much beyond 5x5 it would no longer be feasible, and more sophisticated algorithms would be required.如果远远超过 5x5,它将不再可行,并且需要更复杂的算法。

This is a special case of an integer linear programming problem.这是 整数线性规划问题的一个特例。 The special case of 0-1 integer linear programming is still unfortunately NP-complete, though there exist many algorithms including heuristic ones.不幸的是,0-1 整数线性规划的特殊情况仍然是 NP 完全的,尽管存在许多算法,包括启发式算法。 You can use a built-in library to do this for you.您可以使用内置库为您执行此操作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM