3 回答
TA贡献1815条经验 获得超13个赞
假设键盘存储为位置字典(元组 x,y)和相应的数字作为值,您可以执行以下操作:
import itertools
def distance(p1, p2):
return sum((x1 - x2) ** 2 for x1, x2 in zip(p1, p2))
def neighbors(positions, target):
return [position for position in positions if distance(target, position) < 4]
def numbers(kpad, keys):
return tuple(sorted(map(kpad.get, keys)))
values = list(range(1, 10)) + [0]
positions = list(itertools.product([0, 1, 2], repeat=2)) + [(3, 1)]
keypad = dict(zip(positions, values))
result = {value: numbers(keypad, neighbors(keypad, key)) for key, value in keypad.items()}
print(result)
输出
{0: (0, 7, 8, 9), 1: (1, 2, 4, 5), 2: (1, 2, 3, 4, 5, 6), 3: (2, 3, 5, 6), 4: (1, 2, 4, 5, 7, 8), 5: (1, 2, 3, 4, 5, 6, 7, 8, 9), 6: (2, 3, 5, 6, 8, 9), 7: (0, 4, 5, 7, 8), 8: (0, 4, 5, 6, 7, 8, 9), 9: (0, 5, 6, 8, 9)}
这个想法是为每个位置获取相邻点的值。
更新
要将列表 a 转换为键盘字典,您可以执行以下操作:
data = [[1, 2, 3], [4, 5, 6], [7, 8, 9], [None, 0, None]]
keypad = {(i, j): value for i, sub in enumerate(data) for j, value in enumerate(sub) if value is not None}
其余方法保持不变。
TA贡献1811条经验 获得超6个赞
您可以使用生成器函数:
import re
def all_adjacent(_c, _graph):
_funcs = [lambda x,y:(x+1, y), lambda x,y:(x+1, y+1), lambda x,y:(x+1, y-1), lambda x,y:(x, y+1), lambda x,y:(x-1, y+1), lambda x,y:(x-1, y-1), lambda x,y:(x, y-1), lambda x,y:(x-1, y)]
yield _graph[_c[0]][_c[1]]
for func in _funcs:
a, b = func(*_c)
try:
if a >= 0 and b >= 0:
_val = _graph[a][b]
if _val != ' ':
yield _val
except:
pass
s = """
1 2 3
4 5 6
7 8 9
0
"""
new_data = [re.findall('\d+|\s{2,}', i) for i in filter(None, s.split('\n'))]
final_results = {c:list(all_adjacent((i, d), new_data)) for i, a in enumerate(new_data) for d, c in enumerate(a) if c != ' '}
_result = {int(a):tuple(sorted(map(int, b))) for a, b in final_results.items()}
输出:
{1: (1, 2, 4, 5), 2: (1, 2, 3, 4, 5, 6), 3: (2, 3, 5, 6), 4: (1, 2, 4, 5, 7, 8), 5: (1, 2, 3, 4, 5, 6, 7, 8, 9), 6: (2, 3, 5, 6, 8, 9), 7: (0, 4, 5, 7, 8), 8: (0, 4, 5, 6, 7, 8, 9), 9: (0, 5, 6, 8, 9), 0: (0, 7, 8, 9)}
编辑:将矩阵存储为列表列表:
import re
def all_adjacent(_c, _graph):
_funcs = [lambda x,y:(x+1, y), lambda x,y:(x+1, y+1), lambda x,y:(x+1, y-1), lambda x,y:(x, y+1), lambda x,y:(x-1, y+1), lambda x,y:(x-1, y-1), lambda x,y:(x, y-1), lambda x,y:(x-1, y)]
yield _graph[_c[0]][_c[1]]
for func in _funcs:
a, b = func(*_c)
try:
if a >= 0 and b >= 0:
_val = _graph[a][b]
if _val is not None:
yield _val
except:
pass
new_data = [[1, 2, 3], [4, 5, 6], [7, 8, 9], [None, 0, None]]
final_results = {c:(i, d) for i, a in enumerate(new_data) for d, c in enumerate(a) if c is not None}
_result = {int(a):tuple(map(int, all_adjacent(b, new_data))) for a, b in final_results.items()}
输出:
{1: (1, 4, 5, 2), 2: (2, 5, 6, 4, 3, 1), 3: (3, 6, 5, 2), 4: (4, 7, 8, 5, 2, 1), 5: (5, 8, 9, 7, 6, 3, 1, 4, 2), 6: (6, 9, 8, 2, 5, 3), 7: (7, 0, 8, 5, 4), 8: (8, 0, 9, 6, 4, 7, 5), 9: (9, 0, 5, 8, 6), 0: (0, 9, 7, 8)}
TA贡献1877条经验 获得超1个赞
假设您的矩阵如下所示:
m = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9],
[None, 0, None]
]
您可以蛮力解决您的解决方案,只需遍历矩阵并使用 defaultdict 收集相邻单元格:
from collections import defaultdict
from pprint import pprint
m = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9],
[None, 0, None]
]
rows = len(m)
cols = len(m[0])
# adjacent cells
adjacency = [(i, j) for i in (-1, 0, 1) for j in (-1, 0, 1) if not i == j == 0]
d = defaultdict(list)
for r in range(rows):
for c in range(cols):
cell = m[r][c]
if cell is not None:
d[cell].append(cell)
for x, y in adjacency:
if 0 <= r + x < rows and 0 <= c + y < cols:
adjacent = m[r + x][c + y]
if adjacent is not None:
d[cell].append(adjacent)
# print sorted adjacent cells
pprint({k: tuple(sorted(v)) for k, v in d.items()})
这给出了排序的相邻单元格的字典:
{0: (0, 7, 8, 9),
1: (1, 2, 4, 5),
2: (1, 2, 3, 4, 5, 6),
3: (2, 3, 5, 6),
4: (1, 2, 4, 5, 7, 8),
5: (1, 2, 3, 4, 5, 6, 7, 8, 9),
6: (2, 3, 5, 6, 8, 9),
7: (0, 4, 5, 7, 8),
8: (0, 4, 5, 6, 7, 8, 9),
9: (0, 5, 6, 8, 9)}
添加回答
举报