我需要点子,这不是作业.......
我有以下矩阵,我如何获得重复数字的坐标,
imagen http://image.prntscr.com/image/24ef1e12db9542f9b171170aaefa5751.png
重复[[[0,0],[1,0],[2,0],[0,1],[0,2],[1,2],[1,3],[2] ,2]],[[0,3],[0,4],........]
瞬间代码:
n = [ [1,1,1,3,3],[1,2,1,1,2],[1,2,1,3,3] ]
coordinates = [[-1,0],[0,1],[1,0],[0,-1]]
i = 0
while i < len(n):
j = 0
fila = []
while j < len(n[0]):
for coordinate in coordinates:
X = i + coordinate[0]
Y = j + coordinate[1]
if X >= 0 and X < len(n) and Y >= 0 and Y < len(n[0]):
# I tried with two for in here but its not efficient
j+=1
i+=1
由于
编辑:
预期产出:
组1,分开2,分开3和仅2
重复[[[0,0],[1,0],[2,0],[0,1],[0,2],[1,2],[1,3],[2] ,2]],[[0,3],[0,4]],[[1,1],[2,1]],[[1,4]],[[2,3],[2] ,4]]
答案 0 :(得分:2)
效率不高,因为测试数组多次用于逻辑比较检查,但大多数循环被推送到C级。 同时,它演示了一些有趣的方法,如果你有类似的功能可以探索。
import scipy.ndimage as nd
import numpy as np
n = np.array([ [1,1,1,3,3],[1,2,1,1,2],[1,2,1,3,3] ], dtype=np.int)
def print_coord(val, pos, shape):
print("{}: {}".format(val[0], list(zip(*np.unravel_index(pos, dims=shape)))))
return 0
for val in np.unique(n):
labelled_array, num_features = nd.label(n == val)
nd.labeled_comprehension(n, labelled_array, [1,2,3],
lambda v, p: print_coord(v, p, shape=n.shape), float, 0, True)
输出:
1: [(0, 0), (0, 1), (0, 2), (1, 0), (1, 2), (1, 3), (2, 0), (2, 2)]
2: [(1, 1), (2, 1)]
2: [(1, 4)]
3: [(0, 3), (0, 4)]
3: [(2, 3), (2, 4)]
当您不想保留与该坐标列表匹配的标签时,您当然可以将结果附加到列表中。
答案 1 :(得分:1)
根据您提供给您示例的输出,我提出了以下解决方案:
import sys
def findMax(n, m, mat):
max = -sys.maxint - 1
for i in xrange(n):
for j in xrange(m):
if mat[i][j] > max:
max = mat[i][j]
return max
def doIt(mat):
n, m = len(mat), len(mat[0])
max_val = findMax(n, m, mat)
memo = [None] * (max_val + 1)
for i in xrange(n):
for j in xrange(m):
if memo[mat[i][j]] is None:
memo[mat[i][j]] = [(i, j)]
else:
memo[mat[i][j]].append((i, j))
return {i: item for i, item in enumerate(memo) if item is not None and len(item) > 1}
if __name__ == '__main__':
n = [ [1,1,1,3,3],[1,2,1,1,2],[1,2,1,3,3] ]
print doIt(n)
memo
是一个列表,其中索引表示潜在的重复数字,相应的值是坐标列表。最初memo
初始化为None
,其长度为max
,通过遍历输入矩阵(O(N ^ 2))找到。关键观察 - 如果memo
中的特定数字有多对坐标,则我们发现重复。
答案 2 :(得分:1)
这是一个非Numpy解决方案。它使用itertools.groupby
将坐标分成具有n
中相同值的列表的列表,然后将它们分成由邻居组成的子列表。
from itertools import product, groupby
n = [
[1, 1, 1, 3, 3],
[1, 2, 1, 1, 2],
[1, 2, 1, 3, 3],
]
# Return a value from `n` given a coordinate tuple
def keyfunc(t):
y, x = t
return n[y][x]
# Make a list of coordinate tuples.
# This code assumes that all rows in `n` have the same length
a = list(product(range(len(n)), range(len(n[0]))))
# Sort coordinates by the corresponding value in `n`
a.sort(key=keyfunc)
#Split the sorted coordinates into lists that share the same value...
groups = []
for k, g in groupby(a, key=keyfunc):
# ... and separate those into sublists consisting of neighbours
# We must turn g into a proper list
sublists = []
for t in list(g):
y, x = t
neighbours = [(y-1, x), (y+1, x), (y, x-1), (y, x+1)]
# Search for a sublist that contains a neighbour of `t`
for lst in sublists:
if any(u in lst for u in neighbours):
lst.append(t)
break
else:
# No sublist of neighbours found, start a new one
sublists.append([t])
groups.append((k, sublists))
for row in groups:
print(row)
<强>输出强>
(1, [[(0, 0), (0, 1), (0, 2), (1, 0), (1, 2), (1, 3), (2, 0), (2, 2)]])
(2, [[(1, 1), (2, 1)], [(1, 4)]])
(3, [[(0, 3), (0, 4)], [(2, 3), (2, 4)]])