我只能制作无向图。不知道如何制作有针对性的人。
有什么想法吗?
答案 0 :(得分:1)
为相当漫长的帖子道歉。我有时间在火车上杀人。
我猜你所追求的是一个有向图,表示远离起始位置的所有路径(而不是迷宫的图形表示,曾经可以用来解决任意开始/结束位置)。
(没有冒犯意味着,但是)这听起来像是家庭作业,或者至少是一项非常适合做作业的任务。考虑到这一点,以下解决方案侧重于简单而非性能或优雅。
执行此操作的一种直接方法是首先以更可导航的格式存储地图,然后从开始节点开始执行以下操作:
(参见下面的示例实现)
此时,您最终得到一个directed acyclic graph (DAG),其中起始节点位于树的顶部,而结束节点作为其中一个叶子。在这一点上解决这个问题很容易。请参阅this answer on solving a maze representing as a graph。
构建图形时可能的优化是在找到终点后停止。你最终会得到一个不完整的图表,但是如果你只关心最终的解决方案,这并不重要。
请注意,使用堆栈(倒数第一个)意味着以depth-first方式构建图形,而使用队列(先进先出)将导致breadth-first方法。
您通常希望使用队列(如果目的是寻找最短路径,则首先使用广度。请考虑以下地图:
START
######## ######
######## ######
### b a ######
### ## ######
### ## e ######
### c d ######
######## ######
######## END
#################
如果路径是深度优先遍历的,而在分支a
,则会在a->b
之前采用a->e
路径,最后得到图表:
START
|
a
/ \
b e <-- end, since d already visited
|
c
|
d
\
END
但是,使用广度优先方法,a->e
路径会更早地遇到节点d
,从而产生更短的图形和更好的解决方案:
START
|
a
/ \
b e
| |
c d
|
END
提供的示例输入:
..........
#########.
..........
.#########
......#...
#####...#.
##...####.
##.#......
...#######
e = (0,0)
s = (8,0)
免责声明:为了清晰起见,编写了以下代码,而不是速度。它没有经过全面测试,因此无法保证其正确性,但它应该让您了解可能性。
我们假设输入文件的格式一致。大多数错误检查都是为了简洁而遗漏的。
# regex to extract start/end positions
import re
re_sepos = re.compile("""
^([se])\s* # capture first char (s or e) followed by arbitrary spaces
=\s* # equal sign followed by arbitrary spaces
\( # left parenthesis
(\d+),(\d+) # capture 2 sets of integers separated by comma
\) # right parenthesis
""", re.VERBOSE)
def read_maze(filename):
"""
Reads input from file and returns tuple (maze, start, end)
maze : dict holding value of each maze cell { (x1,y1):'#', ... }
start: start node coordinage (x1,y1)
end : end node coordinate (x2,y2)
"""
# read whole file into a list
f = open(filename, "r")
data = f.readlines()
f.close()
# parse start and end positions from last 2 lines
pos = {}
for line in data[-2:]:
match = re_sepos.match(line)
if not match:
raise ValueError("invalid input file")
c,x,y = match.groups() # extract values
pos[c] = (int(x),int(y))
try:
start = pos["s"]
end = pos["e"]
except KeyError:
raise ValueError("invalid input file")
# read ascii maze, '#' for wall '.' for empty slor
# store as maze = { (x1,y1):'#', (x2,y2):'.', ... }
# NOTE: this is of course not optimal, but leads to a simpler access later
maze = {}
for line_num, line in enumerate(data[:-3]): # ignore last 3 lines
for col_num, value in enumerate(line[:-1]): # ignore \n at end
maze[(line_num, col_num)] = value
return maze, start, end
def maze_to_dag(maze, start, end):
"""
Traverses the map starting from start coordinate.
Returns directed acyclic graph in the form {(x,y):[(x1,y1),(x2,y2)], ...}
"""
dag = {} # directed acyclic graph
queue = [start] # queue of nodes to process
# repeat till queue is empty
while queue:
x,y = queue.pop(0) # get next node in queue
edges = dag[(x,y)] = [] # init list to store edges
# for each neighbour (top, bottom, left, right)
for coord in ((x,y-1), (x,y+1), (x-1,y), (x+1,y)):
if coord in dag.keys(): continue # visited before, ignore
node_value = maze.get(coord, None) # Return None if outside maze
if node_value == ".": # valid path found
edges.append(coord) # add as edge
queue.append(coord) # push into queue
# uncomment this to stop once we've found the end point
#if coord == end: return dag
return dag
if __name__ == "__main__":
maze,start,end = read_maze("l4.txt")
dag = maze_to_dag(maze, start, end)
print dag
答案 1 :(得分:0)
This page提供了一个使用python实现图形的精彩教程。从文章中,这是一个由字典表示的目录图的示例:
graph = {'A': ['B', 'C'],
'B': ['C', 'D'],
'C': ['D'],
'D': ['C'],
'E': ['F'],
'F': ['C']}
答案 2 :(得分:0)
由于您已有列表,请尝试创建Adjacency Matrix而不是字典。
list_of_houses = []
directed_graph = [][]
for i in xrange(len(list_of_houses)):
for i in xrange(len(list_of_houses)):
directed_graph[i][i] = 0
然后,从一个房子到另一个房子的任何新边缘(或连接是否是)
directed_graph[from_house][to_house] = 1
你已经完成了。如果有house_a
到house_b
的边缘,那么directed_graph[house_a][house_b] == 1
。